• 02_线性表


    一、描述线性表

    在一个非空有限的集合中,存在唯一一个被称为“第一个”的数据元素,和唯一一个被称为“最后一个”的数据元素,除第一个之外,每个元素只有一个直接前驱,除最后一个外,每个元素只有一个直接后驱。

    二、线性表基本运算

    构造一个空线性表、判断是否为空、返回线性表中元素的个数,返回线性表中索引 i 的数据元素,排序,拆分,清空,销毁等

    三、线性表顺序存储

      1 #include <stdio.h>
      2 #include <malloc.h>
      3 #include <stdlib.h>
      4 
      5 
      6 //定义一个数据类型 Array 来模拟数组 
      7 struct Array
      8 {
      9     int *pBase;// 数组的首地址
     10     int len;//数组的长度
     11     int count;//数组元素个数 
     12 };
     13 
     14 void initArr(struct Array *pArr,int length);
     15 void showArray(struct Array *pArr);
     16 bool arr_Isempty(struct Array *pArr);
     17 bool arr_full(struct Array* pArr);
     18 //插入元素
     19 bool append_arr(struct Array* pArr,int val); 
     20 bool insert_arr(struct Array* pArr,int pos,int val);
     21 bool delete_arr(struct Array *pArr,int pos);
     22 void inversion_arr(struct Array* pArr);
     23 int main(void)
     24 {
     25     //定义一个结构体变量
     26     struct Array arr;
     27     //初始化
     28     initArr(&arr,6);
     29     //打印数组元素
     30     //showArray(&arr);
     31     //传入数组元素 
     32     append_arr(&arr,1); 
     33     append_arr(&arr,2); 
     34     append_arr(&arr,3); 
     35     append_arr(&arr,4);
     36     append_arr(&arr,5);
     37 //    append_arr(&arr,6);
     38     
     39     insert_arr(&arr,2,88); //1 88 2 3 4 5
     40     delete_arr(&arr,2); 
     41     showArray(&arr);
     42     printf("
    倒置:
    ");
     43     inversion_arr(&arr);
     44     showArray(&arr);
     45 }
     46 
     47 //初始化数组,分配空间,指定长度和元素总个数 
     48 void initArr(struct Array *pArr,int length)
     49 {
     50     pArr->pBase = (int *)malloc(sizeof(struct Array) * length);
     51     if(pArr->pBase == NULL)
     52     {
     53         printf("内存分配失败!");
     54         return;
     55     }
     56     else
     57     {
     58         pArr->len = length;
     59         pArr->count = 0;
     60     }
     61     return ; 
     62 }
     63 //判断数组是否为空
     64 bool arr_Isempty(struct Array *pArr)
     65 {
     66     //如果数组总个数为空,返回true 
     67     if(0 == pArr->count)
     68     {
     69         return true;
     70     }
     71     else
     72     {
     73         return false;
     74     }
     75 }
     76 bool arr_full(struct Array* pArr)
     77 {
     78     if(pArr->count == pArr->len)
     79     {
     80         printf("已满
    ");
     81         return true;
     82     }
     83     else
     84     {
     85         return false; 
     86     }
     87 }
     88 //循环打印数组
     89 void showArray(struct Array *pArr)
     90 {
     91     //首先判断数组元素是否为空
     92     if(arr_Isempty(pArr))
     93     {
     94         printf("数组元素为空!");
     95         return; 
     96     } 
     97     else
     98     {
     99         //循环打印输出
    100         for(int i = 0;i < pArr->count;i++)
    101         {
    102             printf("%d    ",pArr->pBase[i]);
    103         }
    104     }
    105     
    106 }
    107 
    108 bool append_arr(struct Array* pArr,int val)
    109 {
    110     //判断数组是否已满
    111     if (arr_full(pArr))
    112     {
    113         printf("数组已满,插入失败!"); 
    114         return false;
    115     } 
    116     pArr->pBase[pArr->count] = val;
    117     pArr->count++;
    118 }
    119 //插入元素 
    120 bool insert_arr(struct Array* pArr,int pos,int val)
    121 {
    122     if(arr_full(pArr)){
    123         return false;
    124     }
    125     if(pos < 1 || pos > pArr->count + 1){
    126         return false;
    127     }
    128     
    129     int i ;
    130     for (i=pArr->count-1;i >= pos - 1; --i)
    131     {
    132         pArr->pBase[i+1] = pArr->pBase[i];
    133     }
    134     pArr->pBase[pos-1] = val;
    135     pArr->count++;
    136     return true;
    137 }
    138 // 1 88 2 3 4 5   2
    139 bool delete_arr(struct Array *pArr,int pos)
    140 {
    141     if(arr_Isempty(pArr))
    142     {
    143         printf("数组为空,删除元素失败!");
    144         return false;
    145     }
    146     if(pos > pArr->count || pos < 1)
    147     {
    148         printf("范围错误!");
    149         return false;
    150     }
    151     int i;
    152     for(i = pos;i < pArr->count;i++)
    153     {
    154         //printf("
     pArr->pBase[i] : %d
    ",pArr->pBase[i]);
    155         pArr->pBase[i-1] = pArr->pBase[i];
    156     }
    157     pArr->count -- ;
    158     return true;
    159 }
    160 
    161 void inversion_arr(struct Array* pArr)
    162 {
    163     int i = 0;
    164     int j = pArr->count -1 ;//数组是从开始的 
    165     int t = 0;
    166     while(i < j)
    167     {
    168         t = pArr->pBase[i];
    169     //    printf("t : %d
    ",t);
    170     //    printf("j : %d
    ",j);
    171         pArr->pBase[i] = pArr->pBase[j];
    172         pArr->pBase[j] = t;
    173     //    printf(" pBase[i] : %d
    ",pArr->pBase[j]);
    174         ++i;
    175         --j;
    176     }
    177 }
    178  

    四、线性表链式存储

      1 #include<stdio.h>
      2 #include<malloc.h>
      3 #include<stdlib.h>
      4 
      5 //定义了一个 数据类型 
      6 typedef struct Node
      7 {
      8     int data; //数据域 
      9     struct Node* pNext;//指针域 
     10 }NODE,* PNODE;//NODE == struct Node ; PNODE = struct Node*
     11 
     12 PNODE create_list(void);
     13 void traverse_list(PNODE pHead);
     14 bool isempty_list(PNODE pHead);
     15 int length_list(PNODE pHead);
     16 bool insert_list(PNODE pHead,int pos,int val);
     17 bool delete_list(PNODE pHead,int pos,int *val);
     18 void sort_list(PNODE pHead);
     19 
     20 int main(void)
     21 {
     22     int val; 
     23     PNODE pHead = NULL;//struct Node* pHead 指向Node的指针变量
     24     pHead = create_list();//创建一个非循环单链表,单链表头节点地址返回给pHead 
     25     traverse_list(pHead);
     26 /*    if(isempty_list(pHead))
     27     {
     28         printf("链表为空!
    ");
     29     }else
     30     {
     31         printf("链表不为空!
    ");
     32     }
     33 */    
     34     printf("链表的长度:%d.
    ",length_list(pHead));
     35     //insert_list(pHead,1,5); 在首结点前插入
     36 //    insert_list(pHead,5,5);   当要插入的结点大于总长度的时候 
     37 //    printf("插入元素后:
    ");
     38 //    traverse_list(pHead);
     39 //    printf("删除元素后:
    ");
     40 //    delete_list(pHead,1,&val);    
     41 //    printf("被删除的元素为:%d
    ",val);
     42     //traverse_list(pHead);
     43     sort_list(pHead);
     44     traverse_list(pHead);
     45     return 0;
     46 }
     47 
     48 //创建一个链表 
     49 PNODE create_list(void)
     50 {
     51     int len;//链表的长度
     52     int i;
     53     int val;//临时存储数据 
     54     printf("请输入你需要的链表长度len =
    ") ;
     55     scanf("%d",&len);
     56     PNODE pHead = (PNODE)malloc(sizeof(NODE));
     57     if(NULL == pHead)
     58     {
     59         printf("内存分配失败!");
     60         exit(-1); 
     61     } 
     62     
     63     PNODE pTail = pHead;
     64     pTail->pNext = NULL;
     65     for(i = 0;i < len;i++)
     66     {
     67         printf("请输入要存储的数据:
    ");
     68         scanf("%d",&val);
     69         //创建一个个链表
     70         PNODE pNew = (PNODE)malloc(sizeof(NODE));
     71         if(NULL == pNew)
     72         {
     73             printf("pNew内存分配失败!");
     74             exit(-1);
     75         }
     76         pNew->data = val; 
     77         
     78         pTail->pNext = pNew;//把新结点挂在尾结点的后面 
     79         pNew->pNext = NULL;//新结点变成尾结点了 
     80         pTail = pNew;//然后pTail指向新结点变成尾结点 
     81     }
     82      
     83      return pHead;
     84 }
     85 
     86 //遍历链表 
     87 void traverse_list(PNODE pHead)
     88 {
     89     PNODE p = pHead->pNext; // 让p指向首结点
     90     while(NULL != p)
     91     {
     92         printf("%d	",p->data);
     93         p = p->pNext; //p往后移    
     94     } 
     95     printf("
    ");
     96     return;
     97 }
     98 bool isempty_list(PNODE pHead)
     99 {
    100     if(NULL == pHead || pHead->pNext == NULL)
    101     {
    102         return true;
    103     }
    104     else
    105     {
    106         return false;
    107     }
    108 }
    109 
    110 int length_list(PNODE pHead)
    111 {
    112     int i = 0;
    113     PNODE p = pHead->pNext;
    114     while (p != NULL)
    115     {
    116         i++;
    117         p = p->pNext;
    118     }
    119     return i;
    120 }
    121 
    122 //插入 
    123 bool insert_list(PNODE pHead,int pos,int val)
    124 {
    125     int i ;
    126     PNODE pT = pHead;
    127     PNODE pTmp = (PNODE)malloc(sizeof(NODE));
    128     PNODE pNew = (PNODE)malloc(sizeof(NODE));
    129     pNew->data = val;
    130     
    131     if(pos == 1)
    132     {
    133         for(i = 0;i < pos-1;i++)
    134         {
    135             pTmp = pT->pNext;//第一个结点 
    136             pNew = pTmp->pNext; 
    137             pTmp->pNext = pNew;
    138         }
    139     } 
    140     else if(pos > length_list(pHead))
    141     {
    142         for(i = 0;i < length_list(pHead) ;i++){
    143             pT = pT->pNext;
    144         }
    145             pNew->pNext = pT->pNext;
    146             pT->pNext = pNew;    
    147     }
    148     else
    149     {
    150         for(i = 0;i < pos -1;i++)
    151         {
    152             pT = pT->pNext;
    153         }
    154 
    155         pNew->pNext = pT->pNext;
    156         pT->pNext = pNew;
    157     }
    158     
    159 
    160     return true;
    161 }
    162 //删除元素 
    163 bool delete_list(PNODE pHead,int pos,int *val)
    164 {
    165     int i;
    166     if(pos < 1 || pos > length_list(pHead))
    167     {
    168         printf("
    位置超出范围,删除失败!
    ");
    169         exit(-1);    
    170     } 
    171     PNODE pNode = (PNODE)malloc(sizeof(NODE));
    172     PNODE pTmp = pHead;
    173     //printf("
     pos : %d",pos);
    174     for(i = 0;i < pos -1;i++)
    175     {
    176         pTmp = pTmp->pNext;//此时pTmp指向的是首结点
    177         pNode = pTmp->pNext;//此时pTmp指向的是第二个结点,赋给pNode,pNode指向的就是第二个结点
    178         pTmp->pNext = pNode->pNext;//此时获取到的是第三个结点,赋给了pTmp,pTmp指向了第三个结点 
    179         *val = pNode->data;
    180         printf("
    第%d结点的元素是%d.
    ",pos,pNode->data);
    181         free(pNode);
    182     }
    183 }
    184 
    185 void sort_list(PNODE pHead)
    186 {
    187     //从狭义的讲 算法和存储结构有关
    188     //广义讲 算法和存储结构无关 
    189     int i,j,t;
    190     PNODE p,q;
    191     int len = length_list(pHead);
    192     for(i = 0,p = pHead->pNext;i < len -1;i++,p = p->pNext)
    193     {
    194         for(j = i+1,q = p->pNext;j < len;j++ ,q=q->pNext)
    195         {
    196             if(p->data > q->data)//类似数组中的 a[i] > a[j]
    197             {
    198                 t = p->data;//类似数组中的 t= a[i]
    199                 p->data = q->data;//类似数组中的 a[i]= a[j]
    200                 q->data = t;//类似数组中的 a[j]= t
    201             }
    202         }
    203     } 
    204 }

    五、顺序表和链表的比较

    1.如果线性表需要频繁查找,很少进行插入和删除,宜采用顺序表结构,反之,采用链表

    2.线性表个数不能确定的情况下,链表优于顺序表。

  • 相关阅读:
    C# String.Compare 方法测试
    C#checked 与 unchecked
    C#枚举类型
    C#结构体
    C越界和溢出的区别
    python/matlab : 将txt文件中的数据读为numpy数组
    matlab程序里调用python文件
    Python
    Pycharm调试及快捷键技巧
    Pycharm远程连接服务器debug时报错
  • 原文地址:https://www.cnblogs.com/weihengblog/p/8322544.html
Copyright © 2020-2023  润新知