1.1線性表·順序表
阿新 • • 發佈:2021-08-03
大家好,我是Koko~
資料結構是計算機儲存、組織資料的方式。資料結構是指相互之間存在一種或多種特定關係的資料元素的集合。通常情況下,精心選擇的資料結構可以帶來更高的執行或者儲存效率。 資料結構往往同高效的檢索演算法和索引技術有關。
本專欄將針對資料結構相關知識進行梳理及總結。建議搭配C語言版(嚴蔚敏版)資料結構教材使用更佳。
線性表是最常用且最簡單的一種資料結構。一個線性表是n個數據元素的有限序列。在稍複雜的線性表中,一個數據元素可以由若干個資料項組成。在這種情況下,常把資料元素稱為記錄,含有大量記錄的線性表又稱檔案。
同一線性表中的元素必定具有相同特性,即屬同一資料物件,相鄰資料元素之間存在著序偶關係。
1、線性結構的基本特徵:
線性邏輯結構的非形式化描述 一個數據元素的有序(次序)集
(1)集合中必存在唯一的一個“第一元素”
(2)集合中必存在唯一的一個 “最後元素”
(3)除最後元素在外,均有 唯一的後繼
(4)除第一元素之外,均有 唯一的前驅
2、線性表型別的儲存結構----順序對映
線性表具有兩種結構——順序結構和鏈式結構。本節主要講解順序結構所對應的順序表。
順序映象
以 x 的儲存位置和 y 的儲存位置之間某種關係表示邏輯關係<x,y>
通常情況順序映象方法是
令y的儲存位置和x的儲存位置相鄰。
一、順序表的定義
順序表,用一組地址連續的儲存單元依次儲存線性表的資料元素,它的邏輯地址相鄰,實體地址也相鄰(參照一維陣列)。
順序表的優點:簡單、支援隨機訪問、查詢方便、尾插和尾刪效率高。
順序表的缺點:資料的插入和刪除慢(需要挪動後面的資料)。
順序表的結構如下圖所示,它有兩個區域,一個是資料區域類似於陣列,存放使用者儲存的資料,另一個是一個整形變數區,存放已經使用了的區域個數。
定義順序表型別
1 #include<stdio.h> 2 #include<stdlib.h> 3 #define MAXSIZE 20 4 5 //資料元素的型別 6 typedef int ElemType; 7 8 //定義順序表型別 9 typedef struct10 { 11 ElemType a[MAXSIZE]; 12 int length; //順序表的實際長度 13 }SqList, *SqList;
二、順序表的基本操作函式
對順序表,有初始化、列印、插入、刪除、查詢的基本操作。
1、初始化順序表函式
1 Status Init_List(SqList &L) 2 { 3 memset(L.data, 0, sizeof(L));//初始化資料為0 4 L.length = 0; //初始化長度為0 5 return 0; 6 }
2、建立順序表函式
1 //建立線性表 2 void Creat_List(SqList *L) 3 { 4 int i; 5 printf("請輸入線性表的長度: "); 6 scanf("%d",&L->length); 7 for(i=0;i<L->length;i++) 8 { 9 printf("資料 %d =",i); 10 scanf("%d",&(L->a[i])); 11 } 12 }
3、輸出函式
1 //輸出線性表 2 void Out_List(SqList L) 3 { 4 int i; 5 for(i=0;i<=L.length-1;i++) 6 printf("%10d",L.a[i]); 7 }
4、插入函式(插入一個元素)
1 //線上性表的第i個位置插入元素e 2 void Insert_Sq(SqList *L,int i,ElemType e) 3 { 4 int j; 5 if(L->length==MAXSIZE) 6 printf("線性表已滿!\n"); 7 else 8 { 9 if(i<1||i>L->length+1) 10 printf("輸入位置錯!\n"); 11 else 12 { 13 for(j=L->length-1;j>=i-1;j--) 14 L->a[j+1]=L->a[j]; 15 L->a[i-1]=e; 16 L->length++; 17 } 18 } 19 }
5、刪除函式(刪除一個元素)
1 //刪除第i個元素,返回其值 2 ElemType Delete_Sq(SqList *L,int i) 3 { 4 ElemType x; 5 int j; 6 if(L->length==0) 7 printf("空表!\n"); 8 else if(i<1||i>L->length) 9 { 10 printf("輸入位置錯!\n"); 11 x=-1; 12 } 13 else 14 { 15 x=L->a[i-1]; 16 for(j=i;j<=L->length-1;j++) 17 L->a[j-1]=L->a[j]; 18 L->length--; 19 } 20 return(x); 21 }
6、查詢函式(查詢一個值為e的元素,返回它的位置)
1 //查詢值為e的元素,返回它的位置 2 int Locate_Elem(SqList L,ElemType e) 3 { 4 int i=0; 5 while(L.a[i]!=e) 6 i++; 7 if(i<=L.length-1) 8 return(i+1); 9 }
三、順序表的功能操作函式
1、倒置函式(將原順序表直接倒置)
1 //倒置函式 將原順序表直接倒置 2 void Reverse(SqList &L) 3 { 4 if (L.length) 5 for (int i = 0; i<L.length - 1 - i; i++) 6 { 7 int t = L.data[i]; 8 L.data[i] = L.data[L.length - 1 - i]; 9 L.data[L.length - 1 - i] = t; 10 } 11 }
2、奇偶分開並排序
1 //奇偶分開並排序 2 void SplitSort(SqList &L) 3 { 4 int Even = 0; 5 int Odd = L.length - 1; 6 int i = 0; 7 int j = L.length - 1; 8 bool flag = false; 9 if (L.length) 10 for (; i < j; i++, j--) 11 { 12 while (L.data[i] % 2 != 0)i++; 13 while (L.data[j] % 2 == 0)j--; 14 if (L.data[i] % 2 == 0 && L.data[j] % 2 != 0&&i<j) 15 { 16 int temp = L.data[i]; 17 L.data[i] = L.data[j]; 18 L.data[j] = temp; 19 flag = true; 20 } 21 if(!flag) //沒有交換 22 { 23 Even = L.length - 1;//全奇數 24 Odd = 0; //全偶數 25 } 26 } 27 if (flag) 28 { 29 for(int i=0;i<L.length;i++) 30 if (L.data[i] % 2 == 0) 31 { 32 Odd = i; 33 Even = i - 1; 34 break; 35 } 36 } 37 sort(L.data, L.data + Even + 1); 38 sort(L.data + Odd, L.data + L.length); 39 }
四、順序表操作總覽
1 /* 2 Project: sequence_list(資料結構-順序表) 3 */ 4 5 #include<cstdio> 6 #include<cstdlib> 7 #include<cstring> 8 #include<cmath> 9 #include<algorithm> 10 #include<iostream> 11 #define MaxSize 100 12 #define ElemType int 13 #define Status int 14 using namespace std; 15 16 //順序表資料結構 17 typedef struct 18 { 19 ElemType a[MAXSIZE]; 20 int length; //順序表的實際長度 21 }SqList, *SqList; 22 23 //***************************基本操作函式*******************************// 24 25 //初始化順序表函式,構造一個空的順序表 26 Status Init_List(SqList &L) 27 { 28 memset(L.data, 0, sizeof(L));//初始化資料為0 29 L.length = 0; //初始化長度為0 30 return 0; 31 } 32 33 //建立順序表函式 初始化前n個數據 34 void Creat_List(SqList *L) 35 { 36 int i; 37 printf("請輸入線性表的長度: "); 38 scanf("%d",&L->length); 39 for(i=0;i<L->length;i++) 40 { 41 printf("資料 %d =",i); 42 scanf("%d",&(L->a[i])); 43 } 44 } 45 46 //插入函式 位置i插入資料 i及之後元素後移 1=<i<=length+1 47 void Insert_Sq(SqList *L,int i,ElemType e) 48 { 49 int j; 50 if(L->length==MAXSIZE) 51 printf("線性表已滿!\n"); 52 else 53 { 54 if(i<1||i>L->length+1) 55 printf("輸入位置錯!\n"); 56 else 57 { 58 for(j=L->length-1;j>=i-1;j--) 59 L->a[j+1]=L->a[j]; 60 L->a[i-1]=e; 61 L->length++; 62 } 63 } 64 } 65 66 //刪除函式 刪除位置i的元素 i之後的元素依次前移 67 ElemType Delete_Sq(SqList *L,int i) 68 { 69 ElemType x; 70 int j; 71 if(L->length==0) 72 printf("空表!\n"); 73 else if(i<1||i>L->length) 74 { 75 printf("輸入位置錯!\n"); 76 x=-1; 77 } 78 else 79 { 80 x=L->a[i-1]; 81 for(j=i;j<=L->length-1;j++) 82 L->a[j-1]=L->a[j]; 83 L->length--; 84 } 85 return(x); 86 } 87 88 //查詢函式 按位置從小到大查詢第一個值等於e的元素 並返回位置 89 int Locate_Elem(SqList L,ElemType e) 90 { 91 int i=0; 92 while(L.a[i]!=e) 93 i++; 94 if(i<=L.length-1) 95 return(i+1); 96 } 97 98 //倒置函式 將原順序表直接倒置 99 void Reverse(SqList &L) 100 { 101 if (L.length) 102 for (int i = 0; i<L.length - 1 - i; i++) 103 { 104 int t = L.data[i]; 105 L.data[i] = L.data[L.length - 1 - i]; 106 L.data[L.length - 1 - i] = t; 107 } 108 } 109 110 //奇偶分開並排序 111 void SplitSort(SqList &L) 112 { 113 int Even = 0; 114 int Odd = L.length - 1; 115 int i = 0; 116 int j = L.length - 1; 117 bool flag = false; 118 if (L.length) 119 for (; i < j; i++, j--) 120 { 121 while (L.data[i] % 2 != 0)i++; 122 while (L.data[j] % 2 == 0)j--; 123 if (L.data[i] % 2 == 0 && L.data[j] % 2 != 0&&i<j) 124 { 125 int temp = L.data[i]; 126 L.data[i] = L.data[j]; 127 L.data[j] = temp; 128 flag = true; 129 } 130 if(!flag) //沒有交換 131 { 132 Even = L.length - 1;//全奇數 133 Odd = 0; //全偶數 134 } 135 } 136 if (flag) 137 { 138 for(int i=0;i<L.length;i++) 139 if (L.data[i] % 2 == 0) 140 { 141 Odd = i; 142 Even = i - 1; 143 break; 144 } 145 } 146 sort(L.data, L.data + Even + 1); 147 sort(L.data + Odd, L.data + L.length); 148 } 149 150 //清空順序表 151 void ClearList(SqList &L) { 152 L.length = 0; 153 } 154 155 //********************************功能函式*****************************************// 156 157 //輸出功能函式 按位置從小到大輸出順序表所有元素 158 void Out_List(SqList L) 159 { 160 int i; 161 for(i=0;i<=L.length-1;i++) 162 printf("%10d",L.a[i]); 163 } 164 165 //建立順序表函式 166 void Create(SqList &L) 167 { 168 int n; bool flag; 169 L.length = 0; 170 printf("請輸入要建立的順序表長度(>1):"); 171 scanf("%d", &n); 172 printf("請輸入%d個數(空格隔開):", n); 173 flag = CreateList(L, n); 174 if (flag) { 175 printf("建立成功!\n"); 176 PrintList(L); 177 } 178 else printf("輸入長度非法!\n"); 179 180 } 181 182 //插入功能函式 呼叫Insert_Sq完成順序表元素插入 呼叫Out_List函式顯示插入成功後的結果 183 void Insert(SqList &L,int place, ElemType e) 184 { 185 bool flag; 186 printf("請輸入要插入的位置(從1開始)及元素:\n"); 187 scanf("%d%d", &place, &e); 188 flag = Insert_Sq(L, place, e); 189 if (flag) 190 { 191 printf("插入成功!!!\n"); 192 PrintList(L); 193 } 194 } 195 196 //刪除功能函式 呼叫Delete_Sq函式完成順序表的刪除 呼叫Out_List函式顯示插入成功後的結果 197 void Delete(SqList &L,int place;) 198 { 199 bool flag; 200 printf("請輸入要刪除的位置(從1開始):\n"); 201 scanf("%d", &place); 202 flag = Delete_Sq(L, place); 203 if (flag) 204 { 205 printf("刪除成功!!!\n"); 206 PrintList(L); 207 } 208 } 209 210 //查詢功能函式 呼叫LocateElem查詢元素 211 void Locate_Elem(SqList L) 212 { 213 ElemType e; int flag; 214 printf("請輸入要查詢的值:\n"); 215 scanf("%d", &e); 216 flag = Locate_Elem(L, e); 217 if (flag) 218 { 219 printf("該元素位置為:%d\n", flag); 220 } 221 else 222 printf("未找到該元素!\n"); 223 } 224 225 //選單 226 void menu() 227 { 228 printf("********1.建立 2.插入*********\n"); 229 printf("********3.刪除 4.查詢*********\n"); 230 printf("********5.倒置 6.分奇偶排序***\n"); 231 printf("********7.輸出 8.清空*********\n"); 232 printf("********9.退出 *********\n"); 233 } 234 int main() 235 { 236 SqList L; int choice; 237 InitList(L); 238 while (1) 239 { 240 menu(); 241 printf("請輸入選單序號:\n"); 242 scanf("%d", &choice); 243 if (9 == choice) break; 244 switch (choice) 245 { 246 case 1:Create(L); break; 247 case 2:Insert(L); break; 248 case 3:Delete(L); break; 249 case 4:Search(L); break; 250 case 5:Reverse(L); break; 251 case 6:SplitSort(L); break; 252 case 7:PrintList(L); break; 253 case 8:ClearList(L); break; 254 default:printf("輸入錯誤!!!\n"); 255 } 256 } 257 return 0; 258 } 259
以上部分
程式碼和圖片轉自以下兩篇文章,如有侵權,請告知刪除!
「lady_killer9」 《資料結構-順序表基本操作的實現(含全部程式碼)》原文連結:https://blog.csdn.net/lady_killer9/article/details/82695770 「飯_團」 《順序表(一)》
原文連結:https://blog.csdn.net/f__yuan/article/details/97000573