双链表删除一个节点

Posted 快第三个十年

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了双链表删除一个节点相关的知识,希望对你有一定的参考价值。

写了一个删除双链表节点的程序,在这里记录一下,直接上代码,代码中的主要步骤都有注释。

  1 #include <stdio.h>
  2 #include <string.h>
  3 #include <stdlib.h>
  4 #include <assert.h>
  5 typedef struct NODE{
  6     struct NODE *prior;
  7     struct NODE *next;
  8     int value;
  9 }Node;
 10 void print(Node* rootp)
 11 {
 12     if(rootp==NULL)
 13     exit(1);
 14     Node*tmp=rootp->next;
 15     while(tmp)
 16     {
 17         printf("value=%d\n",tmp->value);
 18         tmp=tmp->next;
 19     }
 20 }
 21 int dll_insert(Node *rootp,int value);
 22 int dll_remove(Node *rootp,Node* node);
 23 int main ()
 24 {
 25     Node *p1=(Node*)malloc(sizeof(struct NODE));
 26     if(p1==NULL)
 27     return -1;
 28     p1->prior=NULL;
 29     p1->next=NULL;
 30     //p1->value=10;
 31     int value;
 32     printf("输入要插入的值\n");
 33     while(scanf("%d",&value)==1)
 34     dll_insert(p1,value);
 35 
 36     print(p1);
 37     getchar();
 38     printf("输入要删除的值\n");
 39     Node*del=(Node*)malloc(sizeof(Node));
 40     
 41     scanf("%d",&del->value);
 42     if(dll_remove(p1,del))
 43     {
 44         printf("没有要删除的节点\n");
 45         exit(2);
 46     }
 47     print(p1);
 48     return 0;
 49 }
 50 int dll_remove(Node *rootp,Node* node)
 51 {
 52     assert(node!=NULL);//断言node节点不为空 
 53     Node *this=rootp->next;
 54     
 55      while(this!=NULL)
 56      {
 57          if(this->value==node->value)
 58          break;
 59          this=this->next;
 60      }
 61      if(this->value==node->value)
 62      {
 63          if(this->prior==NULL)//this的前驱是rootp指针
 64          rootp->next=this->next;//先把this前驱的后继指向this的后继 
 65          else
 66          this->prior->next=this->next;
 67          if(this->next==NULL) //this是最后一个节点 
 68          rootp->prior=this->prior;
 69          else//把this后继的前驱指向this的前驱 
 70          this->next->prior=this->prior;
 71          free(this);
 72          return 0;
 73      }
 74     return -1;
 75 }
 76 /*在任何一种情况下,新节点都应该插入this的next,新节点的next
 77      指向next节点*/
 78 /*根节点的next字段指向链表第一个节点,prior字段指向最后一个节点
 79 如果链表为空,这两个字段都为NULL*/ 
 80 /*链表第一个节点的prior字段和最后一个节点的next字段为NULL*/
 81  int dll_insert(Node *rootp,int value)
 82  {
 83      Node* this;
 84      Node* next;
 85      Node* new ;
 86      for(this=rootp;(next=this->next)!=NULL;this=next)
 87      {
 88          if(next->value==value)//双向链表中存在value值,退出 
 89          return 0;
 90          if(next->value>value)//当前值大于要插入的值 
 91          break;
 92      }
 93      new=(Node*) malloc(sizeof(struct NODE));
 94      if(new==NULL)
 95      return -1;
 96      new->value=value;
 97      
 98      /*在任何一种情况下,新节点都应该插入this的next,新节点的next
 99      指向next节点*/
100      new->next=next;
101     this->next=new;
102     if(this!=rootp) 
103     new->prior=this;
104     else
105     new->prior=NULL;//this就是根指针,也就是new为第一个节点,所以prior为NULL
106     if(next!=NULL)
107     next->prior=new;
108     else
109     rootp->prior=new;
110     //next值为NULL说明new为最后一个节点,所以根指针的prior字段指向new
111     return 1;//插入成功 
112  }

 

以上是关于双链表删除一个节点的主要内容,如果未能解决你的问题,请参考以下文章

2.2 在单链表和双链表中删除倒数第K个节点

C语言实现非循环双链表节点的删除(不带头结点)

双链表(二)

Ocaml双链表:从双链表中删除满足条件的节点

单链表和双链表中节点删除的时间复杂度

手把手实现双链表