• 链表基本概念


    这个就是链表储存结构。

    这只是一种链表,即单向链表。还有双向链表,单项循环链表,双向循环链表。

    一个链表由无数个结点组成,每一个结点由数据域(用来储存数据)和指针域(用来储存下一个节点的位置),可以把链表想成一个锁链,那么指针域就是连接两个结点之间的链子

    所以为了表示这种结构,这么写

    1 struct node
    2 {
    3     int data;
    4     node *next;  //因为指向下一个结点,所以类型还是node
    5 }*head, *r, *p;  

    其中head是头结点,整个链表操作都要从这开始,这也就反映出了链表的一个弊端:必须从头找,不能直接调用中间的某个结点。

    p类似于开一个新的结点,r用来连接两个结点。具体看如下代码

     1 #include<cstdio>
     2 #include<iostream>
     3 #include<cmath>
     4 #include<algorithm>
     5 using namespace std;
     6 struct node
     7 {
     8     int data;
     9     node *next;
    10 }*head, *r, *p;
    11 int x;
    12 int main()
    13 {
    14     scanf("%d", &x);
    15     head = new node;    //建立一个新节点 
    16     r = head;
    17     while(x != -1)    //直到输入-1 
    18     {
    19         p = new node;
    20         p -> data = x;    //将输入的x存入数据域 
    21         p -> next = NULL;    //最后的一个结点的next没有,就指向NULL(空指针) 
    22         r -> next = p;    //用来连接新的结点 
    23         r = p;        //r到p,为下一次做准备 
    24         scanf("%d", &x); 
    25     }
    26     //此时链表成功建立,一下将链表中的数据输出 
    27     p = head -> next;     //这里的p的作用和前面的p完全无关,相当于控制循环的变量 
    28     while(p -> next != NULL)
    29     {
    30         printf("%d ", p -> data);
    31         p = p -> next;    //相当于for(int i = 0; i < n; ++i)中的i++ 
    32     }
    33     printf("%d\n", p -> data);//因为是p -> next != NULL,p的下一个没有了就停,所以要在单独输出最后一个p 
    34     return 0;
    35 }

    有必要解释一下这个: -> 。这个东西相当于 p.node 中的 " . " ,用来表示结构体 p 里面的东西。

    如 p -> data = 4; 就是将 p 中的 data 赋值成 4 。

    需要注意的是,当输入 x = -1 时,并没有将 -1 存到链表中。

     

    单向循环链表只用将最后一个结点的指针指向第一个结点即可。

     1     scanf("%d", &x);
     2     head = new node;
     3     r = head;
     4     while(x != -1)    
     5     {
     6         p = new node;
     7         p -> data = x;
     8         p -> next = NULL;
     9         r -> next = p;
    10         r = p;        
    11         scanf("%d", &x); 
    12     }
    13     p -> next = head;    //

    双向链表

    先上个图

    这就是个双向链表。

    可见每一个结点的指针域分别指向前一个结点(前趋)和下一个结点(后缀),那么定义时除了一个 *next 还有一个 *pre

    1 struct node
    2 {
    3     int data;
    4     node *pre, *next;
    5 }*head, *tail, *p;  

    所以构建双向链表时除了前面的结点和新的结点连上,新的结点还要和上一个结点连上。

     1 #include<cstdio>
     2 #include<iostream>
     3 #include<cstring>
     4 #include<algorithm>
     5 #include<cmath>
     6 using namespace std;
     7 struct node
     8 {
     9     int data;
    10     node *pre, *next;
    11 }*head, *tail, *p;
    12 int main()
    13 {
    14     int a; scanf("%d", &a);
    15     head = new node;
    16     head -> next = NULL; head -> pre = NULL;
    17     tail = head;
    18     while(a != -1)
    19     {
    20         p = new node;
    21         p -> data = a;
    22         p -> next = NULL;
    23         p -> pre = tail;
    24         tail -> next = p;
    25         tail = p;
    26         scanf("%d", &a);
    27     }
    28     p = head -> next;
    29     while(p -> next != NULL) //正向输出 
    30     {
    31         printf("%d ", p -> data);
    32         p = p -> next;
    33     }
    34     printf("%d\n", p -> data);
    35     p = tail;
    36     while(p -> pre != NULL)    //反向输出 
    37     {
    38         printf("%d ", p -> data);
    39         p = p -> pre;
    40     }
    41     printf("\n");
    42     return 0;
    43 }

    输入:1 2 3 4 5 -1

    输出:1 2 3 4 5

               5 4 3 2 1

  • 相关阅读:
    【转载】【贪心】各种覆盖问题
    【转载】【知识点总结】NOIP前夕 2014.11.4
    最大子图形问题
    小知识
    Tyvj——P1864 [Poetize I]守卫者的挑战
    Tyvj——P1952 Easy
    BZOJ——2134: 单选错位
    BZOJ——1620: [Usaco2008 Nov]Time Management 时间管理
    BZOJ——1622: [Usaco2008 Open]Word Power 名字的能量
    洛谷 U3357 C2-走楼梯
  • 原文地址:https://www.cnblogs.com/mrclr/p/8321092.html
Copyright © 2020-2023  润新知