当前位置:   article > 正文

单链表的创建,插入与删除_单链表的插入删除建立

单链表的插入删除建立

一,什么是单链表

单链表是由结构体变量与结构体变量连接在一起的数据结构。

链表中的结构体是由数据域和指针域组成的, 而前一个结构体的指针域是指向下一个结构体的,从而将多个结构体连接起来,组成单链表。

  1. struct Node
  2. {
  3. int data;//结构域(存放数据)
  4. struct Node*next;//指针域(指向下一个结构体)
  5. };

二,动态创建一个链表

动态创建一个链表是由动态内存申请和模块化设计(链表的功能,包含的数据)完成。

总的来说,创建一个链表是由一下五个步骤组成

1.创建链表(创建一个表头表示整个链表)

2.创建结点

3.插入结点

4.删除结点

5.打印遍历链表(测试)

1.创建链表

首先,我们应该创建一个表头来表示整个链表,代码如下

  1. struct Node* createList()
  2. {
  3. struct Node* headNode = (struct Node*)malloc(sizeof(Node));//使用malloc函数动态分配空间
  4. //headNode->data = 1;由于我们创建的是表头,二表头不存储数据,所以这里不需要数据域
  5. //headNode成为了一个结构体变量
  6. headNode->next = NULL;
  7. return headNode;
  8. }

2.创建结点

这里创建结点和创建链表相似,只不过这里需要一个数据域,代码如下

  1. struct Node* createNode(int data)
  2. {
  3. struct Node* newNode = (struct Node*)malloc(sizeof(Node));
  4. newNode->data = data;
  5. newNode->next = NULL;
  6. return newNode;
  7. }

3.插入结点

插入节点总共有三种,分别为头插法,尾插法和指定位置插入。这里我们只讲头插法。

头插法,就是将一个新的结点插入表头的后面,使表头的指针域指向新的结点,而新的结点的指针域指向原本头结点指向的结点,代码如下

  1. void insertNodeByHead(struct Node* headNode, int data)
  2. {
  3. //首先,创建插入结点
  4. struct Node* newNode = createNode(data);
  5. newNode->next = headNode->next;//新的结点指向原来表头指向的结点
  6. headNode->next = newNode;//表头指向新结点
  7. }

4.删除结点

删除结点,就是将指定的结点从链表中删除,而删除结点中用处最广泛的就是指定位置删除,而指定位置删除,本质上是从表头开始向后找,当遇到满足删除条件的结点,就将其从链表中删除,然后停止,所以,这种方法只能将离表头最近的满足条件的结点删除。所以说,如果链表有多个相同的结点,则要进行多次指定位置删除才可将所有满足条件的结点删除,也就是说每次删除最多只能删掉一个结点,代码如下

  1. void deleteNodeByhead(struct Node* headNode, int posData)
  2. {
  3. struct Node* posNode = headNode->next;//找出指定位置的结点
  4. struct Node* posNodeFront = headNode;//找出指定位置的前一个结点
  5. if (posNode == NULL)
  6. {
  7. printf("链表为空\n");
  8. }
  9. else
  10. {
  11. while (posNode->data != posData)//如果不符合要求,则向后寻找
  12. {
  13. posNodeFront = posNode;
  14. posNode = posNodeFront->next;
  15. if (posNode == NULL)
  16. {
  17. printf("没有找到相关信息,无法删除\n");
  18. break;
  19. }
  20. }
  21. posNodeFront->next = posNode->next;
  22. free(posNode);//删除该节点
  23. }
  24. }

5.打印遍历链表(测试)

打印链表是从第二个结点开始打印,不包括表头,代码如下

  1. void printList(struct Node* headNode)//打印以headNode为表头的链表
  2. {
  3. struct Node* pMove = headNode->next;//定义一个移动的指针pMove,从第二个结点开始打印
  4. while (pMove)
  5. {
  6. printf("%d\n", pMove->data);//打印pMove中的数据
  7. pMove = pMove->next;//pMove向后走
  8. }
  9. printf("\n");
  10. }

6.以下,我在主函数中尝试了插入和删除的相关操作,代码如下

  1. int main()
  2. {
  3. struct Node* list = createList();
  4. insertNodeByHead(list, 1);
  5. insertNodeByHead(list, 2);
  6. insertNodeByHead(list, 3);
  7. insertNodeByHead(list, 4);
  8. insertNodeByHead(list, 1);
  9. printList(list);
  10. deleteNodeByhead(list, 1);
  11. printList(list);
  12. system("pause");
  13. return 0;
  14. }

下面是结果

下面就是全部代码

  1. #include<stdio.h>
  2. #include<stdlib.h>
  3. struct Node
  4. {
  5. int data;//结构域
  6. struct Node*next;//指针域
  7. };
  8. struct Node* createList()
  9. {
  10. struct Node* headNode = (struct Node*)malloc(sizeof(Node));//使用malloc函数动态分配空间
  11. //headNode->data = 1;由于我们创建的是表头,二表头不存储数据,所以这里不需要数据域
  12. //headNode成为了一个结构体变量
  13. headNode->next = NULL;
  14. return headNode;
  15. }
  16. struct Node* createNode(int data)
  17. {
  18. struct Node* newNode = (struct Node*)malloc(sizeof(Node));
  19. newNode->data = data;
  20. newNode->next = NULL;
  21. return newNode;
  22. }
  23. void printList(struct Node* headNode)//打印以headNode为表头的链表
  24. {
  25. struct Node* pMove = headNode->next;//定义一个移动的指针pMove,从第二个结点开始打印
  26. while (pMove)
  27. {
  28. printf("%d\n", pMove->data);//打印pMove中的数据
  29. pMove = pMove->next;//pMove向后走
  30. }
  31. printf("\n");
  32. }
  33. void insertNodeByHead(struct Node* headNode, int data)
  34. {
  35. //首先,创建插入结点
  36. struct Node* newNode = createNode(data);
  37. newNode->next = headNode->next;//新的结点指向原来表头指向的结点
  38. headNode->next = newNode;//表头指向新结点
  39. }
  40. void deleteNodeByhead(struct Node* headNode, int posData)
  41. {
  42. struct Node* posNode = headNode->next;//找出指定位置的结点
  43. struct Node* posNodeFront = headNode;//找出指定位置的前一个结点
  44. if (posNode == NULL)
  45. {
  46. printf("链表为空\n");
  47. }
  48. else
  49. {
  50. while (posNode->data != posData)//如果不符合要求,则向后寻找
  51. {
  52. posNodeFront = posNode;
  53. posNode = posNodeFront->next;
  54. if (posNode == NULL)
  55. {
  56. printf("没有找到相关信息,无法删除\n");
  57. break;
  58. }
  59. }
  60. posNodeFront->next = posNode->next;
  61. free(posNode);//删除该节点
  62. }
  63. }
  64. int main()
  65. {
  66. struct Node* list = createList();
  67. insertNodeByHead(list, 1);
  68. insertNodeByHead(list, 2);
  69. insertNodeByHead(list, 3);
  70. insertNodeByHead(list, 4);
  71. insertNodeByHead(list, 1);
  72. printList(list);
  73. deleteNodeByhead(list, 1);
  74. printList(list);
  75. system("pause");
  76. return 0;
  77. }

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

闽ICP备14008679号