日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

[数据结构与算法] 单链表的简单demo

發(fā)布時間:2023/12/13 编程问答 21 豆豆
生活随笔 收集整理的這篇文章主要介紹了 [数据结构与算法] 单链表的简单demo 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

Vc6之下編譯通過。。

?

1 /******************************************************* 2 * @: Project: 單鏈表數(shù)據(jù)結(jié)構(gòu)演示 3 * @: File: link_list.h 4 * @: Function: 提供單鏈表操作的數(shù)據(jù)結(jié)構(gòu)定義及方法聲明 5 * @: History: 2013-10-01 22:37:05 6 * @: Author: Alimy 7 *******************************************************/ 8 /******************************************************* 9 * @:頭文件包含 10 *******************************************************/ 11 12 #ifndef __LINK_LIST_H__ 13 #define __LINK_LIST_H__ 14 /******************************************* 15 * @: 數(shù)據(jù)結(jié)構(gòu)定義&一些宏 16 ********************************************/ 17 #define ElemType signed short int // 此例子中的數(shù)據(jù)為有符號短整形,在VC6 中占據(jù)16bits 18 #define StatusType int //操作狀態(tài)為int類型 19 #define OK (StatusType)1 20 #define ERROR (StatusType)0 21 22 typedef struct LNode{ 23 ElemType m_data; // 數(shù)據(jù)域 24 struct LNode *p_next; // 指針域 25 } LNode, *pLinkList; 26 27 //typedef struct LHead{ //頭結(jié)點,其實和 LNode的內(nèi)存結(jié)構(gòu)相似, 28 // int ElemNumber; //數(shù)據(jù)域,可以存儲當(dāng)前線性表的長度,也可以什么也不存儲 29 // struct LNode *p_FirstNode; //指針域指向線性表的第一個元素 30 //}LHead, *pLHead; 31 32 #define DATA_FIELD 0//定義是否讓頭結(jié)點的數(shù)據(jù)域存儲表長信息 1為存儲(頭結(jié)點模式),0為不存儲(非頭結(jié)點模式) 33 34 /******************************************* 35 * @: 外部調(diào)用函數(shù)聲明 36 ********************************************/ 37 extern StatusType CreateList_L(pLinkList *pL,int num);//構(gòu)造num個結(jié)點的單鏈表 38 //extern StatusType _CreateList_L(pLinkList *pL,int num); 39 extern StatusType GetElem_L(pLinkList *pL,int idx_location, ElemType* pe); //獲取單鏈表的元素 40 extern StatusType InsertElem_L(pLinkList *pL,int idx_location,ElemType e);//在單鏈表中插入元素 41 extern StatusType DeleteElem_L(pLinkList *pL,int idx_location,ElemType* pe);//在單鏈表中刪除元素 42 extern void ClearList_L(pLinkList *pL); //整表刪除 43 extern int LocateElem_L(pLinkList *pL,ElemType e); //定位元素 44 extern int GetLength_L(pLinkList *pL); 45 46 extern void MergeList_L1(pLinkList *pLa,pLinkList *pLb,pLinkList *pLc);//將兩個有序鏈表并為一個有序鏈表 47 extern void MergeList_L2(pLinkList *pLa,pLinkList *pLb,pLinkList *pLc);//將兩個有序鏈表并為一個有序鏈表 48 49 50 extern void DisplayList_L(pLinkList *pL); //顯示當(dāng)前所有單鏈表的長度 51 #endif // end of __LINK_LIST_H__ link_list.h

?

1 /******************************************************* 2 * @: Project: 單鏈表數(shù)據(jù)結(jié)構(gòu)演示 3 * @: File: link_list.c 4 * @: Function: 提供單鏈表操作的基本函數(shù)和方法 5 * @: History: 2013-10-01 22:37:37 6 * @: Author: Alimy 7 *******************************************************/ 8 9 /******************************************************* 10 * @: 頭文件包含 11 *******************************************************/ 12 #include "link_list.h" 13 #include <stdio.h> 14 #include <conio.h> // int getch(void); 15 #include <stdlib.h> // int rand(void); malloc(); free(); 16 #include <time.h> // time_t time(time_t *); 17 18 /******************************************************* 19 * @: (外部&內(nèi)部)變量聲明及定義 20 *******************************************************/ 21 22 /******************************************************* 23 * @: (外部&內(nèi)部)函數(shù)聲明及定義 24 *******************************************************/ 25 StatusType CreateList_L(pLinkList *pL,int num);//構(gòu)造num個結(jié)點的單鏈表 26 StatusType GetElem_L(pLinkList *pL,int idx_location, ElemType* pe); //獲取單鏈表的元素 27 StatusType InsertElem_L(pLinkList *pL,int idx_location,ElemType e);//在單鏈表中插入元素 28 StatusType DeleteElem_L(pLinkList *pL,int idx_location,ElemType* pe);//在單鏈表中刪除元素 29 int LocateElem_L(pLinkList *pL,ElemType e); //定位元素 30 int GetLength_L(pLinkList *pL);//獲得表長 31 void ClearList_L(pLinkList *pL); //整表刪除 32 33 void DisplayList_L(pLinkList *pL); //顯示當(dāng)前所有單鏈表的長度 34 35 36 37 38 39 40 /******************************************************* 41 * @: 內(nèi)部函數(shù)具體實現(xiàn) 42 *******************************************************/ 43 44 //ElemType s_data[] = {1,2,3,4,5,6,7,8,9,10,11}; 45 46 /* 47 *@:在堆中構(gòu)造一個單鏈表,并逆序插入num個結(jié)點(頭插法) 48 *@:返回值 49 *@: 構(gòu)造成功返回OK 50 *@: 構(gòu)造失敗返回ERROR 51 **/ 52 StatusType CreateList_L(pLinkList *pL,int num){//構(gòu)造num個結(jié)點的單鏈表 53 LNode* p_Work = NULL; //工作指針 54 int idx = 0; 55 if(*pL!=NULL){ 56 printf("當(dāng)前單鏈表已被初始化,不需要執(zhí)行Create操作 \n"); 57 return ERROR; 58 } 59 60 *pL = (pLinkList)malloc(sizeof(LNode)); 61 if(*pL == NULL){ 62 printf("在堆中申請頭結(jié)點失敗 \n"); 63 return ERROR; 64 } 65 (*pL)->m_data = 0; // 數(shù)據(jù)域可以存儲當(dāng)前單鏈表的長度 66 (*pL)->p_next = NULL; 67 68 srand(time(0)); 69 for(idx=0;idx<num;idx++){ 70 p_Work = (pLinkList)malloc(sizeof(LNode)); //在堆中申請新的結(jié)點 71 if(p_Work==NULL){ 72 printf("在堆中申請結(jié)點出現(xiàn)異常,構(gòu)造單鏈表失敗 \n"); 73 return ERROR; 74 } 75 76 //p_Work->m_data = 10*s_data[idx%10];//(rand()%(10)); //均為10以內(nèi)的整數(shù) 77 p_Work->m_data = (rand()%(100))+1; //暈死,每次生產(chǎn)的隨機數(shù)怎么都一樣 78 p_Work->p_next = (*pL)->p_next; 79 (*pL)->p_next = p_Work; //逆序插入,第一個產(chǎn)生為表尾 80 } 81 82 (*pL)->m_data = num; 83 84 // printf("構(gòu)造單鏈表成功,單鏈表的當(dāng)前長度為 【%d】 \n",(*pL)->m_data); 85 // printf("單鏈表的元素值依次是 \n"); 86 // p_Work = (*pL); //指向頭結(jié)點 87 // idx = 0; 88 // while(p_Work->p_next){// p_ Work->p_next != NULL 89 // idx++; 90 // p_Work = p_Work->p_next; 91 // printf("單鏈表的第【%d】個元素的值為【%d】\n",idx,p_Work->m_data); 92 93 // } 94 printf("構(gòu)造含【%d】個元素的單鏈表成功,按任意鍵去到主菜單\n",(*pL)->m_data); 95 getch(); 96 return OK; 97 } 98 //StatusType _CreateList_L(pLinkList *pL,int num){//構(gòu)造num個結(jié)點的單鏈表(尾插法) 99 // LNode* p_Work = NULL; 100 // LNode* p_NewNode = NULL; //指向新申請結(jié)點 101 // LNode* p_LastNode = NULL; //指向當(dāng)前單鏈表的最后一個結(jié)點 102 // int idx = 0; 103 // if(*pL!=NULL){ 104 // printf("當(dāng)前單鏈表已被初始化,不需要執(zhí)行Create操作 \n"); 105 // return ERROR; 106 // } 107 // 108 // *pL = (pLinkList)malloc(sizeof(LNode));//(建立頭結(jié)點) 109 // if(*pL == NULL){ 110 // if(*pL == NULL){ 111 // printf("在堆中申請頭結(jié)點失敗 \n"); 112 // return ERROR; 113 // } 114 // 115 // } 116 // (*pL)->m_data = 0; // 數(shù)據(jù)域可以存儲當(dāng)前單鏈表的長度 117 // (*pL)->p_next = NULL; 118 // p_LastNode = (*pL); 119 // srand(time(0)); 120 // for(idx=0;idx<num;idx++){ 121 // p_NewNode = (LNode*)malloc(sizeof(LNode)); 122 // if(p_NewNode == NULL){ 123 // printf("在堆中申請新結(jié)點失敗 \n"); 124 // return ERROR; 125 // } 126 // p_NewNode->m_data = (rand()%(10)); 127 // p_NewNode->p_next = NULL; 128 // p_LastNode->p_next = p_NewNode; 129 // p_LastNode = p_NewNode; 130 // } 131 // 132 // (*pL)->m_data = num; 133 // 134 // printf("構(gòu)造單鏈表成功,單鏈表的當(dāng)前長度為 【%d】 \n",(*pL)->m_data); 135 // printf("單鏈表的元素值依次是 \n"); 136 // 137 // p_Work = (*pL); //指向頭結(jié)點 138 // idx = 0; 139 // while(p_Work->p_next){// p_ Work->p_next != NULL 140 // idx++; 141 // p_Work = p_Work->p_next; 142 // printf("單鏈表的第【%d】個元素的值為【%d】\n",idx,p_Work->m_data); 143 // } 144 // printf("構(gòu)造含【%d】個元素的單鏈表成功,按任意鍵去到主菜單",(*pL)->m_data); 145 // getch(); 146 // return OK; 147 //} 148 149 150 151 /* 152 *@:定位pL指向的單鏈表的第idx_location 個元素,并將該元素的值賦值給pe指向的內(nèi)存 153 *@:返回值 154 *@: 定位數(shù)據(jù)成功返回OK 155 *@: 定位數(shù)據(jù)失敗返回ERROR 156 **/ 157 StatusType GetElem_L(pLinkList *pL,int idx_location, ElemType* pe){ //獲取單鏈表的元素 158 int idx = 0; 159 LNode * p_Work = NULL; // 工作指針 160 161 #if DATA_FIELD == 0 162 p_Work = (*pL); //工作指針指向頭指針 163 idx = 0; 164 while(p_Work && idx<idx_location){ // 移動工作指針&計數(shù)判斷是否有 165 p_Work = p_Work->p_next; 166 idx++; 167 // p_Work 指向第idx個結(jié)點 168 } 169 170 if((!p_Work)||(idx>idx_location)){ 171 // printf("索引數(shù)據(jù)有(非頭結(jié)點模式)\n"); 172 return ERROR; 173 } 174 175 *pe = p_Work->m_data; 176 return OK; 177 #else 178 //若頭結(jié)點的數(shù)據(jù)域存儲了單鏈表的表長信息 179 if((idx_location>(*pL)->m_data)||(idx_location<1)){ //索引有誤 180 // printf("索引數(shù)據(jù)有誤(頭結(jié)點模式) \n"); 181 return ERROR; 182 } 183 p_Work = (*pL); 184 idx = 0; //工作指針指向頭結(jié)點,計數(shù)清零 185 for(;idx<idx_location;){ 186 p_Work = p_Work->p_next; 187 idx++; 188 } 189 //此時p_Work指向第idx_location個結(jié)點 190 *pe = p_Work->m_data; 191 return OK; 192 #endif 193 194 } 195 196 197 198 /* 199 *@:在pL指向的單鏈表的第idx_location 個位置插入值為e的元素 200 *@:返回值 201 *@: 插入元素成功返回OK 202 *@: 插入元素失敗返回ERROR 203 *@: 時間復(fù)雜度:O(n) 但是插入一個和插入N個區(qū)別不多,單鏈表適合(比較順序表)插入操作較頻繁的操作 204 205 **/ 206 StatusType InsertElem_L(pLinkList *pL,int idx_location,ElemType e){//在單鏈表中插入元素 207 208 int idx = 0; 209 LNode* p_Work = NULL; 210 LNode* pNewNode = NULL; 211 212 #if DATA_FIELD == 0 213 // to do 2013-10-06 00:10:46 214 p_Work = (*pL); //工作指針指向頭結(jié)點 215 idx = 0; 216 217 while((p_Work)&&(idx<idx_location-1)){ 218 idx++; 219 p_Work = p_Work->p_next; 220 } 221 //正常情況下,p_Work應(yīng)該指向第【idx_location - 1】個元素 222 if((!p_Work)||(idx>idx_location-1)){ 223 printf("要插入元素的索引有誤,請檢查后重新輸入 \n"); 224 return ERROR; 225 } 226 else{ 227 pNewNode = (LNode *)malloc(sizeof(LNode)); 228 if(!pNewNode){ 229 printf("在插入元素時,申請堆空間失敗,插入操作元素失敗 \n"); 230 return ERROR; 231 } 232 else{ 233 pNewNode->m_data = e; 234 pNewNode->p_next = p_Work->p_next; 235 p_Work->p_next = pNewNode; 236 return OK; 237 } 238 239 240 } 241 #else 242 //頭結(jié)點存儲了單鏈表的長度 243 if((idx_location<1)||(idx_location>(*pL)->m_data+1)){ // 元素索引邏輯有誤 244 printf("要插入元素的索引有誤,請檢查后重新輸入 \n"); 245 return ERROR; 246 } 247 else{ 248 p_Work = (*pL); 249 idx = 0; //工作指針指向頭結(jié)點,計數(shù)清零 250 for(;idx<idx_location-1;){ 251 p_Work = p_Work->p_next; 252 idx++; 253 } 254 // p_Work指向第【idx_location-1】個結(jié)點 255 pNewNode = (LNode *)malloc(sizeof(LNode)); 256 if(!pNewNode){ 257 printf("在插入元素時,申請堆空間失敗,插入操作元素失敗 \n"); 258 return ERROR; 259 } 260 else{ 261 pNewNode->m_data = e; 262 pNewNode->p_next = p_Work->p_next; 263 p_Work->p_next = pNewNode; // s->next = p->next; p->next = s; 264 (*pL)->m_data++; //計數(shù)器自加 265 printf("插入元素成功\n"); 266 return OK; 267 } 268 } 269 #endif 270 } 271 272 273 /* 274 *@:在pL指向的單鏈表中尋找第一個值為e的元素,將其索引返回 275 *@: 返回值 276 * 找到值為e的元素--->返回非0 索引值 277 * 沒有找到----> 返回0 278 */ 279 int LocateElem_L(pLinkList *pL,ElemType e){ //定位元素 280 int idx = 0; 281 LNode * p_Work = NULL; 282 if(*pL==NULL){ 283 printf("當(dāng)前單鏈表未被初始化,無法執(zhí)行定位操作 \n"); 284 return 0; 285 } 286 287 p_Work = (*pL); 288 idx = 0; //計數(shù)清零,工作指針指向頭結(jié)點 289 //_Loops: 290 // if(p_Work->p_next!=NULL) 291 // { 292 // p_Work = p_Work->next; 293 // idx++; 294 // if(p_Work->m_data == e) 295 // return idx; 296 // goto _Loops; 297 // } 298 299 while(p_Work->p_next!=NULL){ 300 p_Work = p_Work->p_next; 301 idx++; 302 if(p_Work->m_data == e){ 303 printf("找到單鏈表的第【%d】個元素的值為【%d】",idx,p_Work->m_data); 304 return idx; 305 } 306 } 307 printf("沒有定位到元素"); 308 return 0; // 上述沒有定位到 309 310 311 } 312 313 /* 314 *@:刪除pL指向的單鏈表的第idx_location 個位置的元素,并將被刪除結(jié)點的數(shù)據(jù)域賦值給pe指向的內(nèi)存 315 *@:返回值 316 *@: 刪除元素成功返回OK 317 *@: 刪除元素失敗返回ERROR 318 *@: 時間復(fù)雜度:O(n) 但是刪除一個和刪除N個區(qū)別不多,單鏈表適合(比較順序表)刪除操作較頻繁的操作 319 **/ 320 StatusType DeleteElem_L(pLinkList *pL,int idx_location,ElemType* pe){//在單鏈表中刪除元素 321 int idx = 0; 322 LNode * p_Work = NULL; 323 LNode * p_Temp = NULL; 324 325 #if DATA_FIELD == 0 326 idx = 0; 327 p_Work = (*pL); //工作指針指向頭結(jié)點 328 while((p_Work)&&(idx<idx_location-1)){ 329 idx++; 330 p_Work = p_Work->p_next; 331 } 332 //正常情況下,p_Work應(yīng)該指向第【idx_location - 1】個元素 333 if((!p_Work)||(idx>idx_location-1)){ 334 printf("要刪除位置的索引有誤,請重新輸入 \n"); 335 return ERROR; 336 } 337 else{ 338 p_Temp = p_Work->p_next; //指向要刪除的結(jié)點 339 p_Work->p_next = p_Temp->p_next;//p_Work->p_next = p_Work->p_next->p_next; 340 *pe = p_Temp->m_data; 341 free(p_Temp); 342 return OK; 343 } 344 #else 345 if((idx_location<1)||(idx_location>(*pL)->m_data)){ // 346 printf("要刪除元素位置索引有誤,請檢查輸入 \n"); 347 return ERROR; 348 } 349 else{ 350 p_Work = (*pL); 351 idx = 0; //工作指針指向頭結(jié)點 352 for(;idx<idx_location-1;){ 353 p_Work = p_Work->p_next; 354 idx++; 355 } 356 //p_Work指向第【idx_location - 1 】個結(jié)點 357 p_Temp = p_Work->p_next; 358 p_Work->p_next = p_Temp->p_next;//p_Work->p_next = p_Work->p_next->p_next; 359 *pe = p_Temp->m_data; 360 free(p_Temp); 361 (*pL)->m_data--; 362 return OK; 363 } 364 365 #endif 366 } 367 368 /* 369 * @:獲取pL指向的單鏈表中的元素個數(shù) 370 * @:返回值 371 * 得到長度--->返回非0長度值 372 * 得不到長度---->返回0 373 */ 374 int GetLength_L(pLinkList *pL){//獲得表長 375 376 int idx = 0; 377 LNode * p_Work = NULL; 378 if(*pL==NULL){ 379 printf("當(dāng)前單鏈表未被初始化,無法獲取表長\n"); 380 return 0; 381 } 382 #if DATA_FIELD == 0 383 p_Work = (*pL); 384 idx = 0; //計數(shù)清零,工作指針指向頭結(jié)點 385 while(p_Work->p_next!=NULL){ 386 idx++; 387 p_Work = p_Work->p_next; 388 } 389 printf("當(dāng)前單鏈表共有【%d】個元素\n",idx); 390 return idx; 391 392 #else 393 idx = (*pL)->m_data; 394 printf("當(dāng)前單鏈表共有【%d】個元素\n",idx); 395 396 return idx; 397 398 399 #endif 400 401 } 402 /* 403 *@:刪除pL指向的單鏈表的所有結(jié)點 404 */ 405 406 void ClearList_L(pLinkList *pL){ //整表刪除 407 LNode* p_Work1 = NULL; 408 LNode* p_Work2 = NULL; //工作指針 409 410 if(*pL == NULL){ 411 printf("當(dāng)前單鏈表未創(chuàng)建,無法執(zhí)行整表刪除操作 \n"); 412 return ; 413 } 414 else if((*pL)->p_next == NULL){ 415 printf("當(dāng)前單鏈表為空表,不需要執(zhí)行整表刪除操作 \n"); 416 return; 417 } 418 else{ 419 p_Work1 = (*pL)->p_next; // 指向第一個結(jié)點(如果有的話) 420 while(p_Work1!=NULL){ 421 p_Work2 = p_Work1; 422 p_Work1 = p_Work2->p_next;//指向下一個 423 free(p_Work2); 424 } 425 426 // (*pL)->p_next = NULL; // 頭結(jié)點指向NULL 427 (*pL)->m_data = 0; 428 return ; 429 } 430 } 431 432 /* 433 *@: 輸出顯示pL指向的單鏈表所有的元素 434 */ 435 void DisplayList_L(pLinkList *pL){ //顯示當(dāng)前所有單鏈表的長度 436 437 int idx = 0; 438 LNode* p_Work = NULL; 439 440 if(*pL==NULL){ 441 printf("單鏈表還未構(gòu)建,輸不出東東 \n"); 442 return ; 443 } 444 445 #if DATA_FIELD == 0 446 idx = 0; 447 p_Work = (*pL); // 工作指針指向頭結(jié)點,計數(shù)清零 448 if(p_Work->p_next==NULL){ 449 printf("當(dāng)前單鏈表為空表,沒什么東東好顯示的 \n"); 450 return ; 451 } 452 else{ 453 while(p_Work->p_next){ //(p_Work->p_next!=NULL) 454 idx++; 455 p_Work = p_Work->p_next; 456 printf("單鏈表第【%d】個元素的值為【%d】\n",idx,p_Work->m_data); 457 } 458 return ; 459 } 460 #else 461 if((*pL)->m_data == 0){ 462 printf("當(dāng)前單鏈表的表長為0,沒有數(shù)據(jù)元素,沒有什么好打印的 \n"); 463 return ; 464 } 465 idx = 0; 466 p_Work = (*pL); // 工作指針指向頭結(jié)點,計數(shù)清零 467 printf("單鏈表數(shù)據(jù)如下:\n"); 468 for(;idx<(*pL)->m_data;){ // idx < currentLength (currentLength == (*pL)->m_data or currentLength == GetLength_L ) 469 idx++; 470 p_Work = p_Work->p_next; 471 printf("單鏈表第【%d】個元素的值為【%d】\n",idx,p_Work->m_data); 472 } 473 return ; 474 #endif 475 476 } 477 478 479 480 481 //演示程序中沒有用到的程序 482 483 void MergeList_L1(pLinkList *pLa,pLinkList *pLb,pLinkList *pLc);//歸并兩個單鏈表 484 /* 485 *@:歸并,已知pLa和pLb指向的單鏈表的元素都按非遞減排列 486 * 將La 和Lb中的元素歸并到pLc指向的單鏈表中 487 */ 488 void MergeList_L1(pLinkList *pLa,pLinkList *pLb,pLinkList *pLc){ // 按順序表的方法新建結(jié)點歸并到pLc,形成一個新的表,對原來的那兩個單鏈表沒有損傷 489 LNode * p_WorkLa = NULL; 490 LNode * p_WorkLb = NULL; 491 int Lc_len = 0; 492 *pLc = (LNode *)malloc(sizeof(LNode)); //*pLc進來是是未被初始化的,即(*pLc) == NULL 493 (*pLc)->m_data = 0; 494 (*pLc)->p_next = NULL; // 將pLc指向空表 495 496 497 p_WorkLa = (*pLa)->p_next; 498 p_WorkLb = (*pLb)->p_next; // 初始化時都指向第一個結(jié)點(如果有第一個的話) 499 500 while((p_WorkLa!=NULL)&&(p_WorkLb!=NULL)){ 501 Lc_len++; //一定有可以插入的元素 502 if(p_WorkLa->m_data>=p_WorkLb->m_data){ 503 InsertElem_L(pLc,Lc_len,p_WorkLb->m_data); 504 p_WorkLb = p_WorkLb->p_next; 505 } 506 else{ 507 InsertElem_L(pLc,Lc_len,p_WorkLa->m_data); 508 p_WorkLa = p_WorkLa->p_next; 509 } 510 } 511 512 while(p_WorkLa!=NULL){ 513 Lc_len++; 514 InsertElem_L(pLc,Lc_len,p_WorkLa->m_data); 515 p_WorkLa = p_WorkLa->p_next; 516 } 517 518 while(p_WorkLb!=NULL){ 519 Lc_len++; 520 InsertElem_L(pLc,Lc_len,p_WorkLb->m_data); 521 p_WorkLb = p_WorkLb->p_next; 522 } 523 } 524 525 526 void MergeList_L2(pLinkList *pLa,pLinkList *pLb,pLinkList *pLc){//不新建結(jié)點,就用鏈表把la和lb中的元素用指針連接起來也成為lc的結(jié)點 527 LNode* p_la = NULL; 528 LNode* p_lb = NULL; 529 LNode* p_lc = NULL; 530 531 p_la = (*pLa)->p_next; 532 p_lb = (*pLc)->p_next; // 都指向第一個結(jié)點 533 534 pLc = p_lc = p_la; //用La的頭結(jié)點作為Lc的頭結(jié)點 535 536 while((p_la!=NULL)&&(p_lb!=NULL)){ 537 if(p_la->m_data <= p_lb->m_data){ 538 p_lc->p_next = p_la; 539 p_lc = p_la; // 工作指針移動 540 p_la = p_la->p_next; 541 } 542 else{ 543 pLc->p_next = p_lb; 544 p_lc = p_lb; 545 p_lb = p_lb->p_next; 546 } 547 } 548 549 if(p_la != NULL){ 550 p_lc->p_next = p_la; 551 } 552 553 if(p_lb != NULL){ 554 p_lc->p_next = p_lb; 555 } 556 557 free(*(pLb));//釋放Lb結(jié)點 558 (*pLb)->p_next = NULL;//Lb被直接置為空表了! 559 560 } link_list.c

?

?

1 /******************************************************* 2 * @: Project: 單鏈表數(shù)據(jù)結(jié)構(gòu)演示 3 * @: File: main.c 4 * @: Function: 單鏈表demo主程序 5 * @: History: 2013-10-01 22:36:03 6 * @: Author: Alimy 7 *******************************************************/ 8 9 /******************************************************* 10 * @: 頭文件包含 11 *******************************************************/ 12 #include "link_list.h" 13 #include <stdio.h> 14 #include <conio.h> 15 #include <stdlib.h> 16 17 18 /******************************************************* 19 * @:(外部&內(nèi)部)變量聲明及定義 20 *******************************************************/ 21 22 /******************************************************* 23 * @: (外部&內(nèi)部)函數(shù)聲明及定義 24 *******************************************************/ 25 void printmenu(void); 26 27 28 /******************************************************* 29 * @: 主函數(shù) 30 *******************************************************/ 31 int main(){ 32 pLinkList LinkList_Display = NULL; 33 unsigned char keyValue = 0; 34 int idx = 0; 35 ElemType e = 0; 36 if(OK!=CreateList_L(&LinkList_Display,5)) 37 goto _end; 38 39 while(1){ 40 system("cls"); 41 printmenu(); 42 fflush(stdin); 43 scanf("%c",&keyValue); 44 fflush(stdin); 45 switch(keyValue){ 46 case 'a': 47 printf("請輸入你要插入的位置索引及要插入的數(shù)據(jù)\n"); 48 scanf("%d%d",&idx,&e); 49 printf("你要插入數(shù)據(jù)的位置是 【%d】,要插入的數(shù)據(jù)是【%d】\n",idx,e); 50 InsertElem_L(&LinkList_Display,idx,e); 51 printf("按任意鍵返回主菜單\n"); 52 getch(); 53 break; 54 55 case 'b': 56 printf("請輸入你要刪除單鏈表中的元素的索引\n"); 57 scanf("%d",&idx); 58 printf("你要刪除數(shù)據(jù)的位置是 【%d】\n",idx); 59 if(OK==DeleteElem_L(&LinkList_Display,idx,&e)){ 60 printf("刪除元素成功,被刪除的元素值為 %d \n",e); 61 } 62 printf("按任意鍵返回主菜單\n"); 63 getch(); 64 break; 65 case 'c': 66 printf("請輸入你要得到單鏈表中的元素的索引\n"); 67 scanf("%d",&idx); 68 if(OK!=GetElem_L(&LinkList_Display,idx,&e)){ 69 printf("獲取元素失敗,請檢查相關(guān)輸入是否符合操作條件\n"); 70 } 71 else{ 72 printf("獲取到的元素是 %d \n",e); 73 } 74 printf("按任意鍵返回主菜單\n"); 75 getch(); 76 break; 77 case 'd': 78 printf("請輸入你要定位單鏈表中的元素值\n"); 79 scanf("%d",&e); 80 LocateElem_L(&LinkList_Display,e); 81 printf("按任意鍵返回主菜單\n"); 82 getch(); 83 break; 84 case 'e': 85 idx = GetLength_L(&LinkList_Display); 86 if(LinkList_Display->p_next!=NULL){ 87 printf("當(dāng)前表長為【%d】 \n", idx); 88 } 89 printf("按任意鍵返回主菜單\n"); 90 getch(); 91 break; 92 case 'f': 93 ClearList_L(&LinkList_Display); 94 printf("清除單鏈表完成,按任意鍵返回主菜單\n"); 95 getch(); 96 break; 97 case 'g': 98 DisplayList_L(&LinkList_Display); 99 printf("按任意鍵返回主菜單\n"); 100 getch(); 101 break; 102 case 'h': 103 goto _end; 104 break; 105 default: 106 printf("你的輸入環(huán)節(jié)有誤,清重新輸入 \n"); 107 printf("按任意鍵返回主菜單\n"); 108 getch(); 109 break; 110 } 111 } 112 113 114 115 _end: 116 ClearList_L(&LinkList_Display); // 釋放堆空間 117 if(LinkList_Display!=NULL) 118 free(LinkList_Display); //釋放頭結(jié)點 119 /* 120 121 錯誤代碼 : 122 while(LinkList_Display!=NULL) 123 free(LinkList_Display); 124 125 //剛剛才知道 free(p)之后p還是原來的數(shù),不會變成NULL 126 研究了一下 p自身雖然是指針,但不能通過指針的值并不能改變自身的值,所以說傳地址能改變原元素的值是有條件的 127 再者,傳值就一定改變不了原元素的 值么 128 129 //另外一個測試代碼,VC6下測試結(jié)果符合預(yù)期,其他編譯器未經(jīng)測試 130 // test -- start 131 #include <stdio.h> 132 void changedata(long int pointer){ 133 *((int *)pointer) = 100; 134 return ; 135 136 } 137 int main(void){ 138 int temp = 1000; 139 long int p = (long int)(&temp); // 在VC6中l(wèi)ong int為四個字長,等于指針長度 140 printf("temp = %d \n",temp); 141 changedata(p); 142 printf("temp = %d \n",temp); 143 return 1; 144 } 145 // test--end 146 傳值還是傳址不能被形式表象所迷惑。 147 */ 148 getch(); 149 return 0; 150 151 } 152 153 154 /* 155 *@: 打印演示主菜單 156 *@:返回值(無) 157 */ 158 void printmenu(void){ 159 printf(" 【主菜單】: 請輸入數(shù)據(jù)相應(yīng)對應(yīng)的操作\n"); 160 printf("【a】: 在單鏈表中插入元素\n"); 161 printf("【b】: 在單鏈表中刪除元素\n"); 162 printf("【c】: 在單鏈表中得到元素\n"); 163 printf("【d】: 在單鏈表中定位元素\n"); 164 printf("【e】: 獲取當(dāng)前單鏈表的表長\n"); 165 printf("【f】: 清除單鏈表,整表刪除\n"); 166 printf("【g】: 打印當(dāng)前單鏈表的所有數(shù)據(jù)\n"); 167 printf("【h】: 退出當(dāng)前程序\n"); 168 printf(" 您需要執(zhí)行的操作項是: "); 169 } 170 171 172 173 /* 174 175 單鏈表結(jié)構(gòu)與順序表存儲結(jié)構(gòu)的比較 176 1:存儲分配方式 177 順序表:申請連續(xù)塊空間 178 單鏈表:鏈?zhǔn)缴暾?#xff0c;存儲單元任意 179 2:時間性能 180 查找: 181 順序表:O(1) 182 單鏈表:O(n) 183 刪除&插入: 184 順序表:O(n) 185 單鏈表:第一次為O(n),后續(xù)為O(1) 186 3:空間性能 187 順序表: 188 需要預(yù)分配,分配大了造成浪費;分配小了,容易造成溢出 189 單鏈表: 190 只要 有,隨時可以用 191 192 193 若線性表需要頻繁的查找,很少進行插入&刪除操作,宜采用順序存儲結(jié)構(gòu) 194 反之可以采用鏈?zhǔn)酱鎯Y(jié)構(gòu) 195 196 197 例子: 198 游戲開發(fā)中,對于用戶注冊注冊的個人信息,只讀取居多,宜采用順序存儲結(jié)構(gòu) 199 游戲中的武器或者裝備列表,增加刪除操作更多,宜采用鏈?zhǔn)酱鎯Y(jié)構(gòu) 200 201 202 當(dāng)線性表中的元素個數(shù)變化大或者對應(yīng)用不了解的情況下,最好采用單鏈表結(jié)構(gòu),不必考慮存儲空間的大小問題。 203 若評估知道規(guī)模大致長度,可以用順序表。。 204 205 總之:綜合各種條件考慮! 206 */ main.c

?

(老實說,我對單鏈表的頭結(jié)點有點好奇,

我的想法是為頭結(jié)點單獨管理,然后讓頭結(jié)點的數(shù)據(jù)域來管理單鏈表的長度。。。這樣在插入&刪除等操作中,直接就可以用頭結(jié)點的數(shù)據(jù)域來判斷是否能完成插入&刪除等操作了。。

1 typedef struct LHead{ //頭結(jié)點,其實和 LNode的內(nèi)存結(jié)構(gòu)相似, 2 int LinkListLength; //數(shù)據(jù)域,可以存儲當(dāng)前線性表的長度,也可以什么也不存儲 3 struct LNode *p_FirstNode; //指針域指向線性表的第一個元素 4 }LHead, *pLHead;

?

額。靜態(tài)鏈表&(循環(huán)鏈表&雙向鏈表)就直接跳過了,不寫demo了。。

靜態(tài)鏈表不是在擁有指針機制的其他高級語言使用鏈表的機制。

?

循環(huán)鏈表&雙向鏈表和單鏈表的實現(xiàn)類似。

轉(zhuǎn)載于:https://www.cnblogs.com/alimy/p/3361977.html

總結(jié)

以上是生活随笔為你收集整理的[数据结构与算法] 单链表的简单demo的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。