双向链表的创建
3 node_t* dlinklist_creat(void)
4 {
5 node_t*head=malloc(sizeof(node_t));
6 if(head==NULL)
7 {
8 printf("malloc fail\n");
9 return NULL;
10 }
11 head->next=NULL;
12 head->prev=NULL;
13 return head;
14 }
与单向链表的区别在于结构体多了一个指向前节点的指针
双向链表的头插入
16 void dlinklist_insert_head(node_t *phead,data_t d)
17 {
18 if(phead==NULL)
19 return;
20 node_t *new_p=malloc(sizeof(node_t));
21 if(new_p==NULL)
22 {
23 printf("malloc fail\n");
24 return;
25 }
26 new_p->data=d;
27 new_p->next=phead->next;
28 new_p->prev=phead;
29 phead->next=new_p;
30 if(new_p->next!=NULL)
31 new_p->next->prev=new_p;
32 }
判断链表是否为空
34 int is_empty(node_t*phead)
35 {
36 if(phead->next==NULL)
37 return 1;
38 return 0;
39 }
打印链表
41 void dlinklist_print(node_t*phead,int dir)
42 {
43 if(phead==NULL || is_empty(phead))
44 return;
45 node_t*p=phead->next;
46 if(dir==1)
47 {
48 while(p!=NULL)
49 {
50 printf("%d ",p->data);
51 p=p->next;
52 }
53 }else if(dir == 0)
54 {
55 while(p->next!=NULL)
56 {
57 p=p->next; //p到达尾节点
58 }
59 while(p->prev!=NULL)
60 {
61 printf("%d ",p->data);
62 p=p->prev;
63 }
64 }
65 putchar('\n');
66 return;
67 }
链表长度计算
69 int length(node_t *phead)
70 {
71 if(phead==NULL || is_empty(phead))
72 return 0;
73 node_t *p=phead->next;
74 int cnt=0;
75 while(p!=NULL)
76 {
77 cnt++;
78 p=p->next;
79 }
80 return cnt;
81 }
双向链表尾插入
83 void dlinklist_insert_tail(node_t *phead,data_t d)
84 {
85 if(phead==NULL)
86 return;
87 node_t *p_new=malloc(sizeof(node_t));
88 if(p_new==NULL)
89 {
90 printf("malloc fail\n");
91 return;
92 }
93 node_t *p_end=phead;
94 while(p_end->next!=NULL)
95 {
96 p_end=p_end->next;
97 }
98 p_new->data=d;
99 p_new->next=NULL;
100 p_new->prev=p_end;
101 p_end->next=p_new;
102 }
双向链表查找
104 node_t* dlinklist_find_key(node_t*phead,data_t key)
105 {
106 if(phead==NULL || is_empty(phead))
107 return NULL;
108 node_t*p=phead->next;
109 while(p!=NULL && p->data!=key)
110 {
111 p=p->next;
112 }
113 return p;
114 }
双向链表修改
116 void dlinklist_updata_key(node_t*phead,data_t old_val,data_t new_val)
117 {
118 if(phead==NULL || is_empty(phead))
119 return;
120 node_t*p=dlinklist_find_key(phead,old_val);
121 if(p==NULL)
122 return;
123 p->data=new_val;
124 }
双向链表删除(头删、尾删、指定删)
126 int dlinklist_del_head(node_t*phead) //返回值1代表成功删除,0代表列表无法删除
127 {
128 if(phead==NULL || is_empty(phead))
129 return 0;
130 node_t*p=phead->next;
131 phead->next=p->next;
132 if(p->next!=NULL)
133 {
134 p->next->prev=phead;
135 }
136 free(p);
137 p=NULL;
138 return 1;
139 }
140
141 int dlinklist_del_tail(node_t*phead) //返回值1代表成功删除,0代表列表无法删除
142 {
143 if(phead==NULL || is_empty(phead))
144 return 0;
145 node_t*p=phead->next;
146 while(p->next!=NULL)
147 {
148 p=p->next;
149 }
150 p->prev->next=NULL;
151 free(p);
152 return 1;
153 }
154 int dlinklist_del_key(node_t*phead,data_t key)
155 {
156 if(phead==NULL || is_empty(phead))
157 return 0;
158 node_t*p=dlinklist_find_key(phead,key);
159 if(p==NULL)
160 return 0;
161 p->prev->next=p->next;
162 if(p->next!=NULL)
163 p->next->prev=p->prev;
164 free(p);
165 return 1;
166 }
销毁双向链表
168 int dlinklist_destroy(node_t**phead)
169 {
170 if(*phead==NULL)
171 return 0;
172 if(is_empty(*phead)==1)
173 {
174 free(*phead);
175 *phead=NULL;
176 return 1;
177 }
178 node_t *p=(*phead)->next;
179 while(p)
180 {
181 node_t *p_temp=p;
182 p=p->next;
183 free(p_temp);
184 }
185 free(*phead);
186 *phead=NULL;
187 return 1;
188 }