一、基本概念
单向链表是一种线性数据结构,由一系列节点组成,每个节点包含两部分:数据域(存储数据)和指针域(指向下一个节点的地址)。链表的最后一个节点指向NULL,表示链表结束。与数组不同,链表的内存分配是动态的,插入和删除操作更高效,但随机访问效率较低。
二、特点
(1)动态大小:无需预先分配固定内存,可根据需求动态扩展或收缩。
(2)插入/删除高效:时间复杂度为O(1)(已知位置时),而数组需要移动元素。
(3)内存非连续:节点通过指针链接,物理存储上不要求连续内存空间。
(4)不支持随机访问:必须从头节点开始遍历,访问第n个节点的时间复杂度为O(n)。
三、单向链表的常见操作
1、定义节点结构
c
typedef struct Node {
int data; // 数据域
struct Node *next; // 指针域
} Node;
2、创建链表
初始化一个头节点(或空链表):
c
Node* createList() {
return NULL; // 返回空链表
}
3、插入节点
(1)头部插入:新节点成为头节点。
c
Node* insertAtHead(Node *head, int value) {
Node *newNode = (Node*)malloc(sizeof(Node));
newNode->data = value;
newNode->next = head;
return newNode; // 返回新头节点
}
(2)尾部插入:遍历到链表末尾再插入。
c
Node* insertAtTail(Node *head, int value) {
Node *newNode = (Node*)malloc(sizeof(Node));
newNode->data = value;
newNode->next = NULL;
if (head == NULL) return newNode;
Node *current = head;
while (current->next != NULL) {
current = current->next;
}
current->next = newNode;
return head;
}
4、删除节点
删除指定值的节点:
c
Node* deleteNode(Node *head, int value) {
if (head == NULL) return NULL;
if (head->data == value) {
Node *temp = head->next;
free(head);
return temp;
}
Node *current = head;
while (current->next != NULL && current->next->data != value) {
current = current->next;
}
if (current->next != NULL) {
Node *temp = current->next;
current->next = temp->next;
free(temp);
}
return head;
}
5、遍历链表
c
void traverseList(Node *head) {
Node *current = head;
while (current != NULL) {
printf("%d -> ", current->data);
current = current->next;
}
printf("NULL\n");
}
四、单向链表的优缺点
- 优点 :
- 插入/删除操作高效。
- 内存利用率高,无需预分配空间。
- 缺点 :
- 访问元素需遍历,效率低。
- 指针占用额外内存空间。