# include <stdio.h>
# include <malloc.h>
# include <stdlib.h>typedef struct Node{int data;//數據域struct Node *pNext;//指針域}NODE, *PNODE;
//NODE等價于struct Node
//PNOD等價于struct Node *
//函數聲明PNODE create_list(void);
void traverse_list(PNODE pHead);int main(void){PNODE pHead = NULL;//等價于 struct Node * pHead =NuLL;//生成鏈表pHead = create_list();//create_list()這個函數的功能,創建一個非循環單鏈表,并將該鏈表的頭結點的地址賦值給pHead//輸出鏈表,也就是遍歷鏈表traverse_list(pHead);//traverse表示遍歷的意思return 0;
}PNODE create_list(void){//返回值是一個地址PNODEint len;//用來存放有效結點的個數int i;int val;//用來臨時存放用戶輸入的結點的值/*首先一定要先生成一個臨時的頭結點pHead分配了一個不存放有效數據的頭結點,pHead就指向了頭結點*/PNODE pHead = (PNODE)malloc(sizeof(NODE));//返回到是結點本身的數據類型所以說是NODEif(pHead == NULL){printf("分配失敗,程序終止");exit(-1);}PNODE pTail = pHead;//把pHead的值賦值給pTail,即pHead跟pTail就都指向了頭結點pTail->pNext = NULL;//然后把頭指針給清空,這樣就會導致pTail永遠指向尾結點printf("請輸入您需要生成的鏈表節點的個數: len = ");scanf("%d",&len);for(i=0;i<len;++i){printf("請輸入第%d個結點的值:",i+1);scanf("%d",&val);//現在的val已經存放了結點的值,但是真正的結點并沒有生成,因為真正的結點是兩部分即:指針域和數據域PNODE pNew = (PNODE)malloc(sizeof(NODE));if(pNew == NULL){printf("分配失敗,程序終止");exit(-1);}pNew->data = val;//把pNew生成一個臨時的結點,然后將接收到的val這個結點存放到這個數據域里面去pTail->pNext = pNew;//假設pTail永遠指向尾結點,把pNew掛在尾結點的后面pNew->pNext = NULL;//然后新結點變成尾結點pTail = pNew;//然后pTail就指向尾結點了//關鍵是然后生成這個pTail/*pHead->pNext = pNew;//然后再把臨時結點放到pHead后面pNew->pNext = NUILL;//然后再將臨時結點的指針域給清空,因為臨時結點已經變成最后一個結點啦*/}return pHead;
}
void traverse_list(PNODE pHead){//遍歷的時候也不需要返回值,但是一定需要參數PNODE p =pHead->pNext;//p指向第一個有效結點/*p的值此時有可能為空,如果這個鏈表為空,那么這個鏈表只有一個結點就是所謂的頭結點鏈表即便是空了,也會有一個頭結點的,然后再用pHead指向鏈表為空即:鏈表中只有一個頭結點,沒有有效的結點*/while(p != NULL){//當p不為空的時候也就是p已經指向了一個結點了,只有p不為空就一直輸出即可printf("%d ",p->data);p = p->pNext;}printf("\n");return ;}/*void f(){int i =10;//f()調用完畢之后,i的值就會消失int * p = (int *)malloc(100);//當f()調用完畢之后,p本身的內存就會被釋放掉,因為p是靜態的,但是后面分配的100個字節還會存在}*/