#include <stdio.h> #include <stdlib.h> #include <stdbool.h> #include <string.h> //定義表示學生信息結點的結構體 typedef struct _student { char name[20]; float score; //定義指向鏈表中下一個結點的指針 struct _student* next; }student; void printlist(student*); int main( ) { //第一步:定義指向鏈表頭和尾的指針 student* head = NULL ; student* tail = NULL ; char name[20] = "" ; float score = 0.0f ; int i = 3; bool ishead = true; printf("input student name score\n"); while(i--) { printf("this %d student\n",i); scanf("%s %f",name,&score); //第二步「:根據結點數據創立結點 //首先,用malloc()函數動態申請內存,內存的大小就是一個結點的大小 student* node = malloc(sizeof(student)); //而後將用戶輸入的數據保存到這個結點 strcpy(node->name,name); node->score = score; //第三步:調整節點之間的指向關係 //若是這是鏈表中的第一個結點。 if(ishead) { //將指向鏈表首結點的head指向這個結點 head = node ; //首結點尚無下一個結點 head->next = NULL ; //當前結點就是鏈表的尾結點 tail = node; //首結點已經處理完畢,下一個結點就是普通結點了 ishead = false; } else { //將新結點添加到已有鏈表的末尾 tail->next = node; //將新的結點做爲新的尾結點 tail = node; } }//第四步:重複第二步和第三步,逐個添加結點 //這裏利用一個while循環重複第二步和第三步。 //直到用戶用"Ctrl+z"結束數據輸入爲止 //將尾結點的next設置爲NULL,表示這是鏈表的結束 if(NULL!=tail) tail->next = NULL; else return -1; //對鏈表進行處理… printlist(head); return 0; } void printlist(student* head) { //將首結點做爲當前結點 student* node = head; //判斷當前結點是否爲NULL,若是不是NULL,則輸出其指向的結構體數據 while(NULL!=node) { //利用當前結點結構體數據的指針訪問其數據成員 printf("name: %s,score: %.2f\n",node->name,node->score); //將結點所指向的下一個結點做爲當前結點 node = node->next; } }
#include <stdio.h> #include <stdlib.h> struct grade { int score; struct grade *next; }; typedef struct grade NODE; //typedef爲C語言的關鍵字,做用是爲一種數據類型定義一個新名字。 //使用typedef目的通常有兩個,一個是給變量一個易記且意義明確的新名字, //另外一個是簡化一些比較複雜的類型聲明。 struct grade *create(); //建立鏈表 void insert(NODE *head,NODE *pnew,int i); //插入鏈表 void pdelete(NODE *head,int i); //刪除列表 void display(NODE *head); //輸出鏈表 void Pfree(NODE *head); //銷燬鏈表 int main(int argc, char *argv[]) { struct grade *head,*pnew; head=create(); if (head==NULL) return 0; printf("輸出建立的鏈表:"); display(head); pnew=(NODE *)malloc(sizeof(NODE)); if (pnew==NULL) { printf("建立失敗!"); return 0; } pnew->score=88; insert(head,pnew, 3); //將新節點插入節點3的後面 printf("插入後的鏈表:"); display(head); pdelete(head,3); //刪除節點3 printf("刪除後的鏈表:"); display(head); Pfree(head); return 0; } struct grade *create() { NODE *head,*tail,*pnew; int score; head=(NODE *)malloc(sizeof(NODE)); //建立頭節點。 if (head==NULL) { //建立失敗返回 printf("建立失敗!"); return NULL; } head->next=NULL; //頭節點指針域置NULL tail=head; // 開始時尾指針指向頭節點 printf("輸入學生成績:"); while (1) { //建立鏈表 scanf("%d",&score); if (score<0) //成績爲負是退出循環 break; pnew=(NODE *)malloc(sizeof(NODE)); //建立新節點 if (pnew==NULL) { //建立失敗返回 printf("建立失敗!"); return NULL; } pnew->score=score; //新節點數據域存放輸入的成績 pnew->next=NULL; //新節點指針域置NULL tail->next=pnew; //新節點插入到表尾 tail=pnew; //爲指針指向當前的尾節點 } return head; //返回建立鏈表的頭指針 } void insert(NODE *head,NODE *pnew,int i) { NODE *p; //當前指針 int j; p=head; for (j=0; j<i&&p!=NULL; j++) //p指向要插入的第i個節點 p=p->next; if (p==NULL) { //節點i不存在 printf("與插入的節點不存在!"); return; } pnew->next=p->next; //插入節點的指針域指向第i個節點的後繼節點 p->next=pnew; //犟第i個節點的指針域指向插入的新節點 } void pdelete(NODE *head,int i) { NODE *p,*q; int j; if (i==0) //刪除的是頭指針,返回 return; p=head; for (j=1; j<i&&p->next!=NULL; j++) p=p->next; //將p指向要刪除的第i個節點的前驅節點 if (p->next==NULL) { //代表鏈表中的節點不存在 printf("不存在!"); return; } q=p->next; //q指向待刪除的節點 p->next=q->next; //刪除節點i,也可寫成p->next=p->next->next free(q); //釋放節點i的內存單元 } void display(NODE *head) { NODE *p; for (p=head->next; p!=NULL; p=p->next) printf("%d ",p->score); printf("\n"); } void pfree(NODE *head) { NODE *p,*q; p=head; while (p->next!=NULL) { //每次刪除頭節點的後繼節點 q=p->next; p->next=q->next; free(q); } free(head); //最後刪除頭節點 } void Pfree(NODE *head) { NODE *p,*q; p=head; while (p->next!=NULL) { q=p->next; p->next=q->next; free(q); } free(p); }