zoukankan      html  css  js  c++  java
  • C++学习(三十五)(C语言部分)之 单链表

     单链表 就好比火车

    火车头-->链表头部
    火车尾-->链表尾部
    火车厢-->链表的节点
    火车厢连接的部分-->指针
    火车中的内容-->链表节点的的数据
    链表节点包含数据域和指针域
    数据域存放数据
    指针域存放要连接的节点的首地址

    在造火车的时候 先是火车头 然后是车厢
    --->链表的首节点和之后的节点

    先从内存中申请头结点的存储空间
    --->PLTST phead=(PLTST)malloc(sizeof(LTST));
    首节点在创建时会让指针域指向空
    --->既链表的初始化

    链表连接的规则,要先连接后断开
    对于单链表的插入有两种方法
    1、头插法
    2、尾插法(比较简单的)

    尾插法 申请好一个新的节点后将链表的最后一个节点的指针域指向新节点

    头插法 首先创建新节点,找到链表头节点,将指针指向新节点,将新节点指针指向第二节点

    单链表测试代码笔记如下:

      1 #include<stdio.h>
      2 #include <stdlib.h> //malloc 要用到
      3 
      4 typedef struct Node
      5 {
      6     int data;  //数据域:用来存放数据
      7     struct Node* pNext;  //指针域:用来存储下一个结点地址
      8 }LIST,*PLIST;
      9 
     10 //1. 创建一个火车头.  相当于创建链表 =用函数来创建一个链表的头部
     11 //创建链表的头部
     12 PLIST CreateListHead()
     13 {
     14        //1.1 申请内存
     15     PLIST phead = (PLIST)malloc(sizeof(LIST));
     16     //1.2 判断是否申请成功
     17     if (NULL == phead)
     18     {
     19         printf("头结点的内存申请失败!
    ");
     20         return NULL; 
     21     }
     22     phead->pNext = NULL;
     23     //phead->data   可以赋值也可以不赋值,因为头结点不存储数据
     24     //.它只是用来标记链表的头部
     25     //有表头的链表头结点都不存储数据,只是用来标记链表的头部
     26     return phead;
     27 }
     28 
     29 //2.写一个创建结点的函数,用来申请结点内存
     30 PLIST CreateListNode(int data)
     31 {
     32     PLIST newNode = (PLIST)malloc(sizeof(LIST));
     33     if (NULL == newNode)
     34     {
     35         printf("结点内存申请失败!
    ");
     36         return NULL;
     37     }
     38     newNode->pNext = NULL;
     39     newNode->data = data;
     40     return newNode;
     41 }
     42 
     43 //3.插入一个结点   头部插入  指定位置插入  尾部插入
     44 void InsertListHead(PLIST p_list, int data)//1. 要说明要插入的链表是哪一个 2.要插入的数据
     45 {
     46     //3.1 申请一个结点
     47     PLIST node = CreateListNode(data);
     48     //先连接后断开
     49     node->pNext = p_list->pNext;
     50     p_list->pNext = node;
     51 }
     52 
     53 //4. 尾插法
     54 void InsertListTail(PLIST p_list, int data)
     55 {
     56     //4.1 申请结点内存
     57     PLIST node = CreateListNode(data);
     58     //我们只知道链表的头部  尾部就要去遍历得到
     59     PLIST p_Temp = p_list;
     60     //遍历找到尾结点
     61     while (p_Temp->pNext!=NULL)  //  表达式非0就是真
     62     {
     63         p_Temp = p_Temp->pNext;
     64     }
     65     //循环结束 就是找到了最后一个结点
     66     node->pNext = NULL;
     67     p_Temp->pNext = node;
     68 }
     69 
     70 //在链表p_list中的pos位置插入data
     71 void InsertListAppoint(PLIST p_list, int pos, int data)
     72 {
     73     PLIST node = CreateListNode(data);
     74     PLIST p_Temp1 = p_list;
     75     PLIST p_Temp2 = p_list;
     76     for (int i = 0; i < pos; i++)
     77     {
     78         if (p_Temp1->pNext != NULL)
     79         {
     80             p_Temp1 = p_Temp1->pNext;
     81             if (i>0)
     82             p_Temp2 = p_Temp2->pNext;
     83         }
     84         else
     85         {   //如果pos大于链表结点的个数,就插入到尾部
     86             p_Temp1->pNext = node;
     87             node->pNext = NULL;
     88             return;   //退出函数 不往下执行
     89         }
     90     }
     91     //循环结束  --> 说明我找到了我要插入的位置
     92     node->pNext = p_Temp1;
     93     p_Temp2->pNext = node;
     94 
     95 }
     96 
     97 //  遍历链表的每一个结点
     98 void PrintList(PLIST p_list)
     99 {
    100     PLIST p_Temp = p_list->pNext; //从头部的下一个结点开始输出里面的数据
    101     while (p_Temp)
    102     {
    103         printf("%d -> ", p_Temp->data);//打印结点里面的数据
    104         p_Temp = p_Temp->pNext;
    105     }
    106     printf("NULL
    ");
    107 }
    108 //删除    删除头结点  指定位置删除  尾部删除
    109 //知道这个逻辑     多画图 多写代码  
    110 //后面还会有双向循环链表 要处理四个指针  现在只需要处理两个 双向循环链表不画图很难理解
    111 //画图之后会发现很简单 只需要照着画的图去链接各个指针就OK了
    112 void DeleteListHead(PLIST p_list)  //PLIST p_list=head.
    113 {
    114     PLIST p_Temp = p_list->pNext;
    115     //先链接还是先释放 
    116     p_list->pNext = p_Temp->pNext;  //连接
    117     free(p_Temp);
    118 }
    119 
    120 //不用循环 删除所有结点
    121 void DeleteList(PLIST p_list)//函数会执行5  5 4 3 2 1
    122 {
    123     //满足条件的情况下 自己调用自己
    124     if (p_list->pNext!=NULL)   //if括号里面不是0就是成立
    125     {
    126         DeleteList(p_list->pNext);
    127     }
    128     free(p_list);
    129 
    130 }
    131 
    132 int fun(int n)
    133 {
    134     if (n == 1)
    135     {
    136         return 1;
    137     }
    138     else
    139     {
    140         return n + fun(n - 1);
    141     }  //5 +4+3+2+1    //函数嵌套调用
    142     for (int i = 0; i < 5; i++)
    143     {
    144         for (int j = 1; j < 5; j++)
    145         {
    146               ///内循环结束又回到了外循环
    147         }
    148     }
    149 }
    150 
    151 int main()
    152 {
    153     PLIST head = CreateListHead();  //创建头部 把堆内存的首地址返回给head
    154     for (int i = 1; i <= 5; i++)
    155         InsertListHead(head, i);
    156     PrintList(head);
    157 
    158     ////尾插法
    159     //InsertListTail(head, 98);
    160     //PrintList(head);
    161 
    162     ////指定位置插入
    163     //InsertListAppoint(head, 2, 520);
    164     //PrintList(head);
    165     //InsertListAppoint(head, 88, 520);
    166     //PrintList(head);
    167     //DeleteListHead(head);
    168     //PrintList(head);
    169 
    170     DeleteList(head);
    171     PrintList(head);
    172     head = NULL;
    173     return 0;
    174 }

     附:

  • 相关阅读:
    jquery map.js
    json序列指定名称
    如何将后台传来的json反序列化为前端具体对象
    创建随机码!!
    用户(三次)登录--作业小编完成
    求出1-2+3-4+5------100求和
    if -else 条件语句原理
    联系:中奖彩票小编译
    求出1-100内所有奇数。
    练习题:求1-100所有数偶数
  • 原文地址:https://www.cnblogs.com/Yuuki-/p/10634409.html
Copyright © 2011-2022 走看看