單鏈表-18個基本操作代碼實現C語言


單鏈表-18個基本操作代碼實現C語言

原文地址:https://www.cnblogs.com/actanble/p/6713434.html

無更改,僅復現

 

運行后如圖,運行軟件dev-C++,系統版本win10

 

 

  1 #include<stdio.h>
  2 #include<stdlib.h>
  3 #include<string.h>
  4 
  5 
  6 typedef int elemType;     //定義存入的數據的類型可以是 int char
  7 
  8 typedef struct NODE{      //定義單鏈表的結點類型
  9     elemType element;
 10     struct NODE *next; 
 11 }Node;
 12 
 13 /*             以下是關於線性表鏈接存儲(單鏈表)操作的18種算法        */
 14  
 15 /* 1.初始化線性表,即置單鏈表的表頭指針為空 */
 16 /* 2.創建線性表,此函數輸入負數終止讀取數據*/
 17 /* 3.打印鏈表,鏈表的遍歷*/
 18 /* 4.清除線性表L中的所有元素,即釋放單鏈表L中所有的結點,使之成為一個空表 */
 19 /* 5.返回單鏈表的長度 */
 20 /* 6.檢查單鏈表是否為空,若為空則返回1,否則返回0 */
 21 /* 7.返回單鏈表中第pos個結點中的元素,若pos超出范圍,則停止程序運行 */
 22 /* 8.從單鏈表中查找具有給定值x的第一個元素,若查找成功則返回該結點data域的存儲地址,否則返回NULL */
 23 /* 9.把單鏈表中第pos個結點的值修改為x的值,若修改成功返回1,否則返回0 */
 24 /* 10.向單鏈表的表頭插入一個元素 */
 25 /* 11.向單鏈表的末尾添加一個元素 */
 26 /* 12.向單鏈表中第pos個結點位置插入元素為x的結點,若插入成功返回1,否則返回0 */
 27 /* 13.向有序單鏈表中插入元素x結點,使得插入后仍然有序 */
 28 /* 14.從單鏈表中刪除表頭結點,並把該結點的值返回,若刪除失敗則停止程序運行 */
 29 /* 15.從單鏈表中刪除表尾結點並返回它的值,若刪除失敗則停止程序運行 */
 30 /* 16.從單鏈表中刪除第pos個結點並返回它的值,若刪除失敗則停止程序運行 */
 31 /* 17.從單鏈表中刪除值為x的第一個結點,若刪除成功則返回1,否則返回0 */
 32 /* 18.交換2個元素的位置 */
 33 /* 19.將線性表進行快速排序 */
 34 
 35 /*************************************************************************************************/
 36 
 37 
 38 
 39 
 40 
 41 /*1,初始化線性表,即置單鏈表的表頭為空*/
 42 void initList(Node **pNode){
 43     *pNode=NULL;
 44     printf("inirList函數執行,初始化成功!\n");
 45 } 
 46 
 47 /*2,創建線性表,此函數輸入負數終止讀取數據*/
 48 Node *creatList(Node *pHead){
 49     
 50     Node *p1,*p2;
 51     p1=p2=(Node *)malloc(sizeof(Node));//生成新的頭結點,p1、p2兩個頭指針指向頭結點 
 52     if(p1==NULL||p2==NULL){
 53         printf("內存分配失敗\n");
 54         exit(0);
 55     }
 56     memset(p1,0,sizeof(Node));
 57     
 58     scanf("%d",&p1->element);
 59     p1->next=NULL;
 60     
 61     while(p1->element >0){   //輸入的大於0則繼續否則停止 
 62         if(pHead==NULL){//空表,接入表頭    
 63             pHead=p1;
 64              } 
 65         else{
 66             p2->next=p1;
 67             }
 68             
 69         p2=p1;
 70         p1=(Node *)malloc(sizeof(Node));
 71         
 72         if(p1==NULL||p2==NULL){
 73             printf("內存分配失敗\n");
 74             exit(0);
 75             }
 76         memset(p1,0,sizeof(Node));
 77         scanf("%d",&p1->element);
 78         p1->next=NULL;
 79         
 80     }
 81     printf("CreatList函數執行,鏈表創建成功\n");
 82     return pHead;
 83 } 
 84 /*3,打印鏈表,鏈表的遍歷*/
 85 void printList(Node *pHead){
 86     if(NULL==pHead){
 87         printf("PrintList函數執行,鏈表為空\n");
 88         }
 89     else{
 90         while(NULL!=pHead){
 91             printf("%d",pHead->element);
 92             pHead=pHead->next;
 93         }
 94         printf("\n");
 95     }
 96 }
 97 
 98 /*4,清楚線性表中的所有元素,幾釋放單鏈表中的所有節點,使表為空,null*/ 
 99 void clearList(Node *pHead){
100     
101     Node *pNext;
102     
103     if(pHead==NULL){
104         printf("clearListh函數執行,鏈表為空");
105         return; 
106         }
107     while (pHead->next!=NULL){
108         pNext=pHead->next;
109         free(pHead);
110         pHead=pNext;
111         }
112     printf("clearList函數執行,鏈表已經清除"); 
113 }
114 
115 /*5,返回鏈表的長度*/
116 int sizeList(Node *pHead){
117     int size=0;
118     
119     while(pHead!=NULL){
120         size++;
121         pHead=pHead->next;
122         }
123     printf("sizeList函數執行,鏈表的長度為%d\n",size);
124     return size;
125 }
126 
127 /*6,檢擦鏈表是否為空,若空返回1,否則返回0*/
128 int isEmptyList(Node *pHead){
129     if(pHead==NULL){
130         printf("isEmptyList函數執行,鏈表為空"); 
131         return 1;
132         }
133     else{
134         printf("isEmptyList函數執行,鏈表非空");
135         return 0;
136         }
137 }
138 /*7,按位置查找,返回鏈表中第post節點的數據,若post超出范圍,則停止程序運行*/
139 int getElement(Node *pHead,int pos){
140     int i=0;
141     if(pos<1){
142         printf("getElemnet函數執行,pos值非法!");
143         return 0; 
144     }
145     if(pHead==NULL){
146         printf("getElemnet函數執行,鏈表為空"); 
147     }
148     while(pHead&&i!=pos){
149         i++;
150         pHead=pHead->next;
151     }
152     if(!pHead||i<pos){
153         printf("getElement函數執行,pos值超出表的長度\n");
154         return 0;
155         }
156     printf("getElement函數執行,位置%d中的元素位置為%d\n",pos,pHead->element);
157     return 1;
158     
159 }
160 /*從單一倆表中查找具有得頂值x的第一個元素,成功則返回改結點data域的存儲位置,否則返回NULL*/
161 elemType *getElemAddr(Node *pHead,elemType x){
162     
163     if(NULL==pHead){
164         printf("getEleAddr函數執行,鏈表為空");
165         return NULL; 
166     }
167     if(x<0){
168         printf("getEleArdd函數執行,給定值X不合法\n");
169         return NULL;
170     }
171     while((pHead->element!=x)&&(NULL!=pHead->next)){//判斷鏈表是否為空,並且是否存在查找的元素 
172         pHead=pHead->next; 
173     }
174     if (pHead->element!=x){
175         printf("getElemAddr函數執行,在鏈表中沒有找到x的值\n");
176         return NULL;
177     }
178     else{
179         printf("getElemAddr函數執行,元素%d的地址為0x%x\n",x,&(pHead->element));
180         
181     }
182     return &(pHead->element);
183 }
184 /*9,修改鏈表中第pos個點x的值,修改成功返回1,否則返回0*/
185 int modifyElem(Node *pNode,int pos,elemType x){
186     
187     Node *pHead;
188     pHead=pNode;
189     int i=0;
190     if(NULL==pHead){
191         printf("modityElem函數執行,鏈表為空");
192         return 0;
193     }
194     if(pos<1){
195         printf("modityElem函數執行,pos值非法\n");
196         return 0;
197     }
198     if(pos>i){
199         printf("modityElem函數執行,pos值超過鏈表長度\n");
200         return 0; 
201     }
202     while(pHead!=NULL){
203         
204         ++i;
205         if(i==pos){
206             break;
207         }
208         pHead=pHead->next;
209     }
210     pNode=pHead;
211     pNode->element=x;
212     printf("modifyElem函數執行,修改第%d點的元素為%d\n",pos,x);
213     return 1;
214     
215 }
216 
217 
218 
219 
220 
221 
222 /*10,向單鏈表的表頭插入一個元素*/
223 int insertHeadList(Node **pNode,elemType insertElem){
224     
225     Node *pInsert;
226     pInsert=(Node *)malloc(sizeof(Node));
227     if(pInsert==NULL)  exit(1);
228     memset(pInsert,0,sizeof(Node));
229     pInsert->element=insertElem;
230     pInsert->next=*pNode;
231     *pNode=pInsert; 
232     printf("insertHeadList函數執行,向單鏈表的表頭插入元素%d成功\n",insertElem);
233     return 1; 
234 }
235 /*11,向單鏈表的隊尾添加一個元素*/
236 int insertLastList(Node *pNode,elemType insertElem){
237     
238     Node *pInsert;
239     Node *pHead;
240     Node *pTmp;
241     
242     pHead=pNode;
243     pTmp=pHead;
244     pInsert=(Node *)malloc(sizeof(Node));
245     if(pInsert==NULL)  exit(1);
246     memset(pInsert,0,sizeof(Node));
247     pInsert->element=insertElem;
248     pInsert->next=NULL;
249     while(pHead->next!=NULL){
250         
251         pHead=pHead->next;
252     }
253     pHead->next=pInsert;
254     printf("insertLastList函數執行,向單鏈表的隊尾添加元素%d成功\n",insertElem);
255     return 1;
256 }
257 /*12,向單鏈表中的第pos個節點插入元素為x的節點,成功返回1,否則后返回0*/
258 int isAddPos(Node *pNode,int pos,elemType x){
259     
260     Node *pHead;
261     pHead=pNode;
262     Node *pTmp;
263     int i=0;
264     
265     if(NULL==pHead){
266         printf("AddPos函數執行,鏈表為空");
267         return 0; 
268     }
269     if(pos<1){
270         printf("AddPos函數執行,pos值非法");
271         return 0;
272     }
273     while(pHead!=NULL){
274         ++i;
275         if(i==pos){
276             break;
277         }
278         pHead=pHead->next;
279     }
280     if(i<pos){
281         printf("AddPos函數執行,pos值超出鏈表的長度");
282         return 0; 
283     }
284     pTmp=(Node *)malloc(sizeof(Node));
285     if(pTmp==NULL) exit(1);
286     memset(pTmp,0,sizeof(Node));
287     pTmp->next=pHead->next;
288     pHead->next=pTmp;
289     pTmp->element=x;
290     
291     printf("AddPos函數執行成功,像結點%d后插入數值%d\n",pos,x);
292     return 1;
293 }
294 /*13,向單鏈表插入元素x節點,是的插入后仍有序*/
295 int OrrderList(Node *pNode,elemType x){
296     //注意如果此數值要排到行尾要修改本代碼
297     Node *pHead=pNode;
298     pHead=pNode;
299     Node *pTmp;
300     
301     if(NULL==pHead){
302         printf("OrrderList函數執行,鏈表為空\n");
303         return 0; 
304     } 
305     if(x<1){
306         printf("OrrderList函數執行,x值非法\n");
307         return 0; 
308     } 
309     while(pHead!=NULL){
310         if((pHead->element)>x){
311             break;
312         }
313         pHead=pHead->next;
314     }
315     if(pHead==NULL){
316         printf("OrrderList函數執行,該函數中沒有該值\n");
317         return 0; 
318     } 
319     
320     pTmp=(Node *)malloc(sizeof(Node));
321     if(pTmp==NULL) exit(1);
322     memset(pTmp,0,sizeof(Node));
323     pTmp->next=pHead->next;
324     pHead->next=pTmp;
325     pTmp->element=x;
326     
327     printf("OrrderList函數成功插入數值%d\n",x);
328     return 1;
329 }
330 /*14,從單鏈表中刪除頭結點並返回其值,失敗則停止程序運行*/
331 int DelHeadList(Node **pList){
332     
333     Node *pHead;
334     pHead=*pList;
335     if(pHead!=NULL){
336         printf("DelHeadList函數執行,函數首元素為%d刪除成功\n",pHead->element);
337     }
338     else{
339         printf("DelHeadList函數執行,倆鳥為空");
340         return 0;
341     }
342     *pList=pHead->next;
343     return 1;
344 }
345 /*15,從鏈表中刪除表尾節點並返回其值,若失敗停止程序運行*/
346 int DelLastList(Node *pNode){
347     
348     Node *pHead;
349     Node *pTmp;
350     
351     pHead=pNode;
352     while(pHead->next!=NULL){
353         
354         pTmp=pHead;
355         pHead=pHead->next;
356     }
357     printf("鏈表尾刪除原元素%d成功\n",pHead->element);
358     free(pHead);
359     pTmp->next=NULL; 
360     return 1;
361 }
362 /*16,從鏈表中刪除第pos個結點並返回他的值,失敗則停止程序運行*/
363 int DelPos(Node *pNode,int pos){
364     
365     Node *pHead;
366     pHead=pNode;
367     Node *pTmp;
368     int i=0;
369     
370     if(NULL==pHead){
371         printf("DelPos函數執行,鏈表為空");
372         return 0;
373     }
374     if(pos<1){
375         printf("DlePos函數之心,pos值非法");
376         return 0;
377     }
378     while(pHead!=NULL){
379         ++i;
380         if(i==pos){
381             break;
382         }
383         pTmp=pHead;
384         pHead=pHead->next;
385     }
386     if(i<pos){
387         printf("DelPos函數執行,pos值超出鏈表長度");
388         return 0; 
389     }
390     printf("DelPos函數執行成功,結點%d刪除數值%d\n",pos,pHead->element);
391     return 1;
392 }
393 /*17,從單鏈表中刪除值為x的第一個結點,若刪除成功返回1, 否則返回0*/
394 int Dlex(Node **pNode,int x){
395     
396     Node *pHead;
397     Node *pTmp;
398     pHead=*pNode;
399     int i=0;
400     
401   if(NULL==pHead){    
402         printf("Delx函數執行,鏈表為空");
403         return 0;    
404     }
405     if(x<0){
406         printf("Delx函數執行,給定值x不合法\n");
407         return 0;
408     }
409     while((pHead->element!=x)&&(NULL!=pHead->next)){
410         
411         i++;
412         pTmp=pHead;
413         pHead=pHead->next;
414         
415     }
416     if(pHead->element!=x){
417         printf("Delx函數執行,在鏈表中沒有找到x值\n");
418         return 0;
419     }
420     if((i==0)&&(NULL!=pHead->next)){
421         printf("Delx函數執行,在鏈表首部找到此袁術,此袁術已經被刪除");
422         free(pHead);
423         return 1; 
424     }
425     printf("Delx函數執行首個為%d元素被刪除\n");
426     free(pHead);
427     return 1;
428 } 
429 /*18,交換兩個元素的位置*/
430 int exchange2pos(Node *pNode,int pos1,int pos2){
431     
432     Node *pHead;
433     int *pTmp;
434     int *pInsert;
435     int a;
436     int i=0;
437     
438     if(pos1<1||pos2<1){
439         printf("DelPos函數執行,pos值非法\n");
440         return 0;
441     }
442     pHead=pNode;
443     while(pHead!=NULL){
444         ++i;
445         if(i==pos1){
446             break;
447         }
448         pHead=pHead->next;
449         
450     }
451     if(i<pos1){
452         printf("DelPos函數執行,pos1值超出鏈表長度\n");
453                 return 0;
454     }
455     pTmp=&(pHead->element);
456     i=0;
457     pHead=pNode;
458     while(pHead!=NULL){
459         ++i;
460         if(i==pos2){
461             break;
462         } 
463         pHead=pHead->next;
464     }
465         if(i<pos2){
466         printf("DelPos函數執行,pos2值超出鏈表長度\n");
467                     return 0;
468     }
469     pInsert=&(pHead->element);
470     a=*pTmp;
471     *pTmp=*pInsert;
472     *pInsert=a;
473     
474     printf("DelPos函數執行,交換第%d個和第%d個點的值\n",pos1,pos2);
475     return 1;
476     }
477     
478 int swap(int *p1,int *p2){
479     int a;
480     if(*p1>*p2){
481         a=*p1;
482         *p1=*p2;
483         *p2=a;
484     }
485     return 0;
486 }
487 
488 /*19,將鏈表進行冒泡排序*/
489 int Arrange(Node *pNode){
490     
491     Node *pHead;
492     pHead=pNode;
493     
494     int a=0,i,j;
495     if(NULL==pHead){
496         printf("Arrange函數執行,鏈表為空\n");
497         return 0;
498     }
499     while(pHead!=NULL){
500         ++a;
501         pHead=pHead->next;
502     }
503     
504     pHead=pNode;
505     for(i=0;i<a-1;i++){
506         
507         for(j=1;j<a-i;j++){
508             swap(&(pHead->element),&(pHead->next->element));
509             pHead=pHead->next;
510         }
511         pHead=pNode;
512     }
513     printf("Arrange函數執行,鏈表排序完畢!\n");
514     return 0;
515 }
516 
517 
518 
519 
520 int main()
521 {
522     Node *pList=NULL;
523     int length=0;
524     
525     elemType posElem;
526     
527     initList(&pList);
528     printList(pList);
529     
530     pList=creatList(pList);
531     printList(pList);
532     
533     sizeList(pList);
534     printList(pList);
535     
536     isEmptyList(pList);
537     
538     
539     posElem=getElement(pList,3);
540     printList(pList);
541     
542     getElemAddr(pList,5);
543     
544     modifyElem(pList,4,1);
545     printList(pList);
546     
547     
548     insertHeadList(&pList,5);
549     printList(pList);
550     
551     insertLastList(pList,6);
552     printList(pList);
553     
554     
555     isAddPos(pList,4,5);
556     printList(pList);
557     
558     
559     OrrderList(pList,6);
560     printList(pList);
561     
562     
563     DelHeadList(&pList);
564     printList(pList);
565     
566         
567     DelLastList(pList);
568     printList(pList);
569     
570     
571     DelPos(pList,3);
572     printList(pList);
573     
574     
575     Dlex(&pList,5);
576     printList(pList);
577     
578     
579     exchange2pos(pList,2,5);
580     printList(pList);
581     
582     Arrange(pList);
583     printList(pList);
584     
585     clearList(pList);
586     return 0;
587     
588 }

 

總結:

進一步理解怎樣構造函數、調用、函數之間的關系。

memset函數與L=(linklist)malloc(sizeof(Node))作用?

malloc函數:

L=(linklist)malloc(sizeof(Node))作用是生成一個新結點做頭結點,頭指針L指向頭結點

memset函數:
void * memset (void * p,int c,size_t n);
其中,指針p為所操作的內存空間的首地址,c為每個字節所賦的值,n為所操作內存空間的字節長度,也就是內存被賦值為c的字節數。
在使用memset時經常要注意的它是以字節為單位進行賦值的,所賦值的范圍是0x00~0xFF。若想要對一個double或int型的數組賦值時,就特別需要注意這一點:
 
 
 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM