手把手写数据结构之双向链表操作

  1 define NAME_LEN    20    //名字最大长度
  2 
  3 //函数入口检测(宏)
  4 #define TEST(arg) if(arg == NULL){
  5     printf("Invalid arg..................
");
  6     return -1;
  7 }
  8 
  9 typedef enum sex//性别封装
 10 {
 11     b ,            //
 12     g ,            //
 13 }E_SEX;
 14 
 15 typedef struct stu_info//学生信息封装
 16 {
 17     int num;                //学号
 18     char name[NAME_LEN+1];    //姓名
 19     E_SEX sex;                //性别
 20 }STU_INFO;
 21 
 22 typedef struct stu_node//结点信息
 23 {
 24     STU_INFO stu;            //学生信息
 25     struct stu_node *prev;    //结点指针前驱
 26     struct stu_node *next;    //结点指针后驱
 27 }NODE;
 28 
 29 
 30 typedef struct link_info
 31 {
 32     int node_count;//结点个数
 33     NODE *head;        //指向首元结点的指针
 34 }LINK_INFO;
 35 
 36 
 37 
 38 
 39 
 40 
 41 
 42 //创建结点
 43 static NODE *__Create_Node__(STU_INFO stu)
 44 {
 45     NODE *new_node = (NODE *)malloc(sizeof(NODE));
 46     if(NULL == new_node)
 47     {
 48         perror("Create_Node");
 49         return NULL;
 50     }
 51 
 52     new_node ->stu = stu;
 53     new_node->next = NULL;
 54     new_node->prev = NULL;
 55 
 56     return new_node;
 57 }
 58 
 59 /*************************************************
 60 *Des:    查找某个结点是否存在
 61 *Ret:    成功返回结点,失败返回NULL;
 62 **************************************************/
 63 static NODE *__Find_Node__(LINK_INFO *plist, int num)
 64 {
 65     if(NULL == plist)
 66     {
 67         printf("Invalid arg.......
");
 68         return NULL;
 69     }
 70 
 71     NODE *pnode = plist->head;
 72     while(NULL != pnode)
 73     {
 74         if(pnode->stu.num == num)
 75             break;
 76         pnode = pnode->next;
 77     }
 78 
 79     return pnode;
 80 }
 81 
 82 /*************************************************
 83 *Des:    创建学生信息链表
 84 *Ret:    成功返回0,失败返回-1;
 85 **************************************************/
 86 int Stu_Ceate_Link(LINK_INFO **plist)
 87 {
 88     TEST(plist);//函数入口检测
 89 
 90     *plist = (LINK_INFO *)malloc(sizeof(LINK_INFO));
 91     if(NULL == *plist)
 92     {
 93         perror("Create Link");
 94         return -1;
 95     }
 96 
 97     (*plist)->node_count = 0;
 98     (*plist)->head = NULL;
 99     
100     return 0;
101 }
102 
103 /*************************************************
104 *Des:    判断学生信息链表是否为空
105 *Ret:    真空:1 ,假空:0
106 **************************************************/
107 int Stu_Is_Empty(LINK_INFO *plist)
108 {
109     return ((NULL == plist->head) ? 1 : 0);
110 }
111 
112 /*************************************************
113 *Des:    添加结点到链表(按num排好序)
114 *Ret:    成功返回0,失败返回-1;
115 **************************************************/
116 int Stu_Add_Node(LINK_INFO *plist, STU_INFO stu)
117 {
118     TEST(plist);//函数入口检测
119 
120     NODE *tmpnode = NULL, *pnode = plist->head;
121 
122     if(__Find_Node__(plist, stu.num) != NULL)
123     {
124         printf("Have this Node!
");
125         return -1;
126     }
127 
128     //创建结点
129     NODE *new_node = __Create_Node__(stu);
130     if(NULL == new_node)
131         return -1;
132     
133     if(Stu_Is_Empty(plist))//当链表为空
134     {
135         plist->head = new_node;
136     }
137     else    //链表非空
138     {
139         while(NULL != pnode)
140         {
141             if(pnode->stu.num > stu.num)
142                 break;
143             tmpnode = pnode;
144             pnode = pnode->next;
145         }
146         if(NULL == pnode)//添加到尾结点后
147         {
148             tmpnode->next = new_node;
149             new_node->prev = tmpnode;
150         }
151         else
152         {
153             if(NULL == tmpnode)//添加到头结点前
154             {
155                 new_node->next = plist->head;
156                 plist->head->prev = new_node;
157                 plist->head = new_node;
158             }
159             else//其它
160             {
161                 tmpnode->next = new_node;
162                 new_node->prev = tmpnode;
163                 new_node->next = pnode;
164                 pnode->prev = new_node;
165             }
166         }
167         
168     }
169     
170     plist->node_count++;
171 
172     return 0;
173 }
174 
175 /*************************************************
176 *Des:    删除学生信息
177 *Ret:    成功返回0,失败返回-1;
178 **************************************************/
179 int Stu_Delete_Node(LINK_INFO *plist, int num)
180 {
181     TEST(plist);//函数入口检测
182 
183     NODE *pnode = NULL;
184     if(NULL == (pnode = __Find_Node__(plist, num)))//1
185     {
186         return -1;
187     }
188 
189     //只有1个节点
190     if(pnode == plist->head && pnode->next == NULL)
191     {
192         plist->head = NULL;
193     }
194 
195     //2.是头结点
196     else if(pnode == plist->head)
197     {
198         plist->head = pnode->next;
199         pnode->next->prev = NULL;
200         //plist->head->prev = NULL;
201     }
202     //3.是最后一个节点
203     else if(pnode->next == NULL)
204     {
205         pnode->prev->next = NULL;
206     }
207     //4.其他节点
208     else
209     {
210         pnode->prev->next = pnode->next;
211         pnode->next->prev = pnode->prev;
212     }
213 
214     free(pnode);
215 
216     plist->node_count--;
217 
218     return 0;
219 }
220 
221 
222 /*************************************************
223 *Des:    遍历学生信息
224 *Ret:    成功返回0,失败返回-1;
225 **************************************************/
226 int Stu_Traverse(LINK_INFO *plist)
227 {
228     TEST(plist);//函数入口检测
229 
230     if(Stu_Is_Empty(plist))
231     {
232         printf("The list is empty!
");
233         return -1;
234     }
235 
236     NODE *pnode = plist->head;
237 printf("###################################################
");
238     printf("num	  name		sex	
");
239     while(NULL != pnode)
240     {
241         if(pnode->stu.sex == 0)
242             pnode->stu.sex += 98;
243         else
244             pnode->stu.sex += 102;
245         
246         printf("%-10d%-10s	%c
", pnode->stu.num,
247                             pnode->stu.name, pnode->stu.sex);
248         pnode = pnode->next;
249     }
250 
251 printf("###################################################
");
252     
253     return 0;
254 }
255 
256 /*************************************************
257 *Des:    清空链表操作
258 *Ret:    成功返回0,失败返回-1;
259 **************************************************/
260 int Stu_Empty_Link(LINK_INFO *plist)
261 {
262     TEST(plist);//函数入口检测
263 
264     if(Stu_Is_Empty(plist))
265     {
266         printf("The is list is empty!
");
267         return -1;
268     }
269     
270     NODE *tmpnode = NULL, *pnode = plist->head;
271     while(pnode != NULL)
272     {
273         tmpnode= pnode; 
274         pnode = pnode->next;
275     }
276     
277     plist->head = NULL;
278     plist->node_count = 0;
279 
280     return 0;
281 }
282 
283 
284 /*************************************************
285 *Des:    销毁链表
286 *Ret:    成功返回0,失败返回-1;
287 **************************************************/
288 int Stu_Destory_Link(LINK_INFO **plist)
289 {
290     TEST(plist);
291 
292     //清空链表
293     if(Stu_Empty_Link(plist) < 0)
294         return -1;
295 
296     free(*plist);
297 
298     *plist = NULL;
299 
300     return 0;
301 }
原文地址:https://www.cnblogs.com/xuyh/p/3238395.html