当前位置:   article > 正文

双链表的排序,合并_合并双向链表

合并双向链表
  1. /*双向链表*/
  2. #include <stdio.h>
  3. #include <stdlib.h>
  4. #include <string.h>
  5. /*基础操作*/
  6. //1.定义
  7. typedef int data_t; //错误1 分号忘了加
  8. typedef struct node_t{
  9. data_t data;
  10. struct node_t *prior, *next; //错误2是struct node_t,而不是node_t
  11. }dlinklist;
  12. //2.创建表,初始化表
  13. dlinklist *create_dlinklist()
  14. {
  15. dlinklist *head = (dlinklist*)malloc(sizeof(dlinklist)); //malloc的用法不熟悉
  16. if(NULL == head) return NULL;
  17. head->data = -1;
  18. head->next = head->prior = NULL;
  19. return head;
  20. }
  21. //3.求表长
  22. int get_len_dlinklist(dlinklist *head)
  23. {
  24. int len = 0;
  25. if(NULL == head) return NULL;
  26. dlinklist *p = head->next;//错误是head.next 空表是只有头结点的表,头结点不算长度
  27. while(p != NULL) //错误是p!=NULL
  28. {
  29. len++;
  30. p = p->next;
  31. }
  32. return len;
  33. }
  34. //4.判空
  35. int dlinklist_is_empty(dlinklist *head)
  36. {
  37. if(NULL == head) return NULL;
  38. return ((head->next == head->prior)?1:0);
  39. }
  40. //5.打印
  41. void show_dlinklist(dlinklist *head)
  42. {
  43. if(NULL == head) return NULL;
  44. dlinklist *p = head->next;
  45. while(p != NULL)
  46. {
  47. printf("%d ",p->data);
  48. p = p->next;
  49. }
  50. printf("\n");
  51. }
  52. //6.清空链表
  53. void clear_dlinklist(dlinklist *head)
  54. {
  55. if(NULL == head) return NULL;
  56. dlinklist *p = head->next;
  57. dlinklist *q = NULL;
  58. head->next = NULL;
  59. while(p != NULL)
  60. {
  61. q = p->next;
  62. free(p);
  63. p = q; //p向后移一位
  64. }
  65. }
  66. //7.销毁链表??
  67. int destory_dlinklist(dlinklist** head)
  68. {
  69. free(*head);
  70. head = NULL;
  71. return 0;
  72. }
  73. /*增删改查*/
  74. //1.头插法
  75. int insert_head_dlinklist(dlinklist* head, data_t val)
  76. {
  77. if(NULL == head) return -1;
  78. //准备new 节点
  79. dlinklist *new = (dlinklist *)malloc(sizeof(dlinklist));
  80. new->data = val; //
  81. new->next = NULL;
  82. new->prior = NULL;
  83. //头插法 插入
  84. if(head->next == NULL)
  85. {
  86. new->next = head->next;
  87. new->prior = head;
  88. head->next = new;
  89. }else
  90. {
  91. new->next = head->next;
  92. head->next->prior = new;
  93. new->prior = head;
  94. head->next = new;
  95. }
  96. return 0;
  97. }
  98. /*题目*/
  99. //1.删除结点p
  100. //找到结点p
  101. dlinklist *get_node_dlinklist(dlinklist *head, int i)
  102. {
  103. dlinklist *p = head->next;
  104. int j = 1;
  105. while (p != head && j < i)
  106. {
  107. p = p->next;
  108. j++;
  109. }
  110. while (p == head | j > i)
  111. {
  112. return -1;
  113. }
  114. return p;
  115. }
  116. int del_node_dlinklist(dlinklist *head, int i, data_t e)
  117. {
  118. dlinklist *p = NULL;
  119. if(!(p = get_node_dlinklist(head,i))) return -1;
  120. e = p->data;
  121. p->prior->next = p->next;
  122. p->next->prior = p->prior;
  123. free(p);
  124. return 0;
  125. }
  126. //2.在p结点之后插入一个节点
  127. int insert_dlinklist(dlinklist *head, int i, data_t e)
  128. {
  129. dlinklist *p = NULL;
  130. if(!(p = get_node_dlinklist(head,i))) return -1;
  131. dlinklist *s = (dlinklist *)malloc(sizeof(dlinklist));
  132. s->data=e;
  133. s->next = p->next;
  134. s->prior = p;
  135. p->next->prior = s;
  136. p->next =s;
  137. }
  138. //3.逆序双向表
  139. dlinklist *reverse(dlinklist *head)
  140. {
  141. if(NULL == head || NULL == head->next) return head;
  142. //指向首元结点
  143. dlinklist *first = head->next;
  144. //指向第二个节点
  145. dlinklist *second = first->next;
  146. //首元结点与后续节点断开
  147. first->next = NULL;
  148. dlinklist *third = NULL;
  149. while(second)
  150. {
  151. third = second->next;
  152. second->prior = NULL;
  153. second->next = first;
  154. first->prior = second;
  155. //使下一节点成为当前节点
  156. first = second;
  157. //继续循环
  158. second = third;
  159. }
  160. //将最后一个节点的前驱节点赋值为头结点指针
  161. first->prior = head;
  162. // 将头结点与后续节点连接
  163. head->next = first;
  164. return head;
  165. }
  166. //4.合并有序表?
  167. dlinklist *merge(dlinklist *A, dlinklist *B)
  168. {
  169. dlinklist *r, *t, *p, *q;
  170. r = A;
  171. p = r->next;
  172. r->next = NULL;
  173. p->prior = NULL;//断开连接,单独取出A的首元素
  174. t = B;
  175. //先将A中p所指剩余结点插入新链表中
  176. while (p != NULL)
  177. {
  178. //用q指向p的下一个结点
  179. q = p->next;
  180. //将p与新链表A中的结点比较有无相同值
  181. while (r != NULL)
  182. {
  183. if (r->data == p->data)
  184. {
  185. //若相同则删除p所指结点,取链表中下一个值
  186. free(p);
  187. break;
  188. }
  189. r = r->next;
  190. }
  191. if (r == NULL)//若无相同值
  192. {
  193. //将p结点插入到新链表中
  194. p->next = A->next;
  195. p->prior = A;
  196. if (A->next != NULL)
  197. {
  198. A->next->prior = p;
  199. }
  200. A->next = p;
  201. }
  202. p = q;
  203. r = A;
  204. }
  205. //先将B中t所指剩余结点插入新链表中
  206. r = A;
  207. while (t != NULL)
  208. {
  209. //用q指向t的下一个结点
  210. q = t->next;
  211. //将t与新链表A中的结点比较有无相同值
  212. while (r != NULL)
  213. {
  214. if (r->data == t->data)
  215. {
  216. //若相同则删除t所指结点,取链表中下一个值
  217. free(t);
  218. break;
  219. }
  220. r = r->next;
  221. }
  222. if (r == NULL)//若无相同值
  223. {
  224. //将p结点插入到新链表中
  225. t->next = A->next;
  226. t->prior = A;
  227. if (A->next != NULL)
  228. {
  229. A->next->prior = t;
  230. }
  231. A->next = t;
  232. }
  233. t = q;
  234. r = A;
  235. }
  236. return A;
  237. }
  238. //5.排序
  239. dlinklist *sort_dlinklist(dlinklist *head) //函数返回值为头指针,形参也为头指针
  240. {
  241. int i=0,j=0;
  242. int n= get_len_dlinklist(head); //调用统计节点个数的函数
  243. dlinklist *p=head; //定义两个临时指针来进行数据处理
  244. dlinklist *pn=head; //p和pn总是两个相邻的节点,且pn在p之后
  245. //****冒泡排序****//
  246. for(i=0;i<n;i++)
  247. {
  248. p=head->next;
  249. pn=p->next;
  250. for(j=0;j<n-1-i;j++)
  251. {
  252. if(p->data < pn->data) //判断,条件成立之后交换位置
  253. {
  254. if(pn->next==NULL) //判断是否为尾节点
  255. {
  256. //**交换位置代码**//
  257. p->next=pn->next;
  258. pn->prior=p->prior;
  259. pn->next=p;
  260. p->prior->next=pn;
  261. p->prior=pn;
  262. //**位置交换结束**//
  263. }
  264. else
  265. {
  266. //**交换位置代码**//
  267. p->next=pn->next;
  268. pn->prior=p->prior;
  269. pn->next->prior=p;
  270. p->prior->next=pn;
  271. //下一行请注意//
  272. pn->next=p;
  273. p->prior=pn;
  274. //**位置交换结束**//
  275. pn=p->next; //位置交换结束之后进行指针偏移,pn指向p的下一个节点
  276. }
  277. }
  278. else //条件不成立
  279. {
  280. p=p->next;
  281. pn=p->next;
  282. //如果未发生位置交换,则两个指针都要发生偏移
  283. }
  284. }
  285. }
  286. return head;
  287. }
  288. int main(int argc, char *argv[])
  289. {
  290. int a[6] = {1,3,5,7,9,11};
  291. int b[6] = {2,4,6,8,10,12};
  292. dlinklist* head1 = create_dlinklist();
  293. for(int i = 0; i < 6; i++)
  294. {
  295. insert_head_dlinklist(head1,a[6-i-1]);
  296. }
  297. printf("list1:");
  298. show_dlinklist(head1);
  299. dlinklist* head2 = create_dlinklist();
  300. for(int i = 0; i < 6; i++)
  301. {
  302. insert_head_dlinklist(head2,b[6-i-1]);
  303. }
  304. printf("list1:");
  305. show_dlinklist(head2);
  306. del_node_dlinklist(head1,2, 5); //删除的节点为第2位,从1开始数起
  307. show_dlinklist(head1);
  308. insert_dlinklist(head1, 4, 98);
  309. show_dlinklist(head1);
  310. reverse(head1);
  311. show_dlinklist(head1);
  312. sort_dlinklist(head1);
  313. show_dlinklist(head1);
  314. merge(head1, head2);
  315. show_dlinklist(head1);
  316. sort_dlinklist(head1);
  317. show_dlinklist(head1);
  318. return 0;
  319. }

运行结果

 

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/我家小花儿/article/detail/905222
推荐阅读
相关标签
  

闽ICP备14008679号