鏈表是線性表的鏈式存儲結構。可視為一串珠子:數據是珠子,next 指針是穿珠子的線。優勢在於動態內存管理、插入刪除 O(1)(定位後)、無需預分配容量。
typedef struct Node {
int data; // 數據域
struct Node *next; // 指針域
} Node;
typedef struct {
Node *head; // 頭節點(哨兵節點)
int count; // 節點計數
} List;
void initList(List *list) {
list->head = (Node*)malloc(sizeof(Node));
list->head->next = NULL;
list->count = 0;
}
void createList(List *list) {
int arr[10] = {1,2,3,4,5,6,7,8,9,10};
for (int i = 0; i < 10; i++) {
Node *p = (Node*)malloc(sizeof(Node));
p->data = arr[i];
p->next = list->head->next;
list->head->next = p;
list->count++;
}
}
void printList(List *list) {
Node *p = list->head->next;
while (p) {
printf("%d ", p->data);
p = p->next;
}
putchar('\n');
}
int search(List *list, int val) {
Node *p = list->head->next;
int pos = 0;
while (p) {
pos++;
if (p->data == val) return pos;
p = p->next;
}
return -1; // 未找到
}
void deleteNode(List *list, int val) {
int pos = search(list, val);
if (pos == -1) { printf("值不存在\n"); return; }
Node *prev = list->head;
Node *curr = list->head->next;
while (curr) {
if (curr->data == val) {
prev->next = curr->next;
free(curr);
list->count--;
break;
}
prev = curr;
curr = curr->next;
}
}
void insertAfter(List *list, int pos, int val) {
if (pos < 0 || pos > list->count) { printf("位置非法\n"); return; }
Node *p = list->head;
for (int i = 0; i < pos; i++) p = p->next; // 移動到第 pos 個節點
Node *q = (Node*)malloc(sizeof(Node));
q->data = val;
q->next = p->next;
p->next = q;
list->count++;
}
int main() {
List list;
initList(&list);
createList(&list);
printf("初始鏈表: "); printList(&list); // 10 9 8 7 6 5 4 3 2 1
deleteNode(&list, 5);
printf("刪除5後: "); printList(&list); // 10 9 8 7 6 4 3 2 1
insertAfter(&list, 1, 99); // 第1個節點(10)後插入
printf("插入99後: "); printList(&list); // 10 99 9 8 7 6 4 3 2 1
return 0;
}
| 概念 | 本質 | 實現方式 | 典型操作 |
|---|---|---|---|
| 鏈表 | 數據結構 | 節點+指針 | 增刪查改 |
| 隊列 | 抽象數據類型(ADT) | 可用鏈表/數組實現 | 先進先出(FIFO) |
| 棧 | 抽象數據類型(ADT) | 可用鏈表/數組實現 | 後進先出(LIFO) |
關鍵理解:隊列/棧是「接口規範」,鏈表是「實現手段」。同一個隊列可用鏈表實現(鏈隊列)或循環數組實現(順序隊列)。