链表的基本操作
链表是数据存储的一种链式结构,使用链表存储的数据元素,其物理存储位置是随机的。数据元素随机存储,并通过指针表示数据之间逻辑关系的存储结构就是链式存储结构。
链表的节点
链表中每个数据的存储都由以下两部分组成:
数据元素本身,其所在的区域称为数据域;
指向直接后继元素的指针,所在的区域称为指针域
一个存储 {1,2,3} 的完整链表结构如图
定义链表结构体:
typedef struct LinkNode {
char data;
struct LinkNode *next;
} LNode, *LinkList, *NodePtr;
创建链表结点:
LinkList initLinkList(){
NodePtr tempHeader = (NodePtr)malloc(sizeof(LNode));
tempHeader->data = '\0';
tempHeader->next = NULL;
return tempHeader;
}
打印链表:
void printList(NodePtr paraHeader){
NodePtr p = paraHeader->next;
while (p != NULL) {
printf("%c", p->data);
p = p->next;
}// Of while
printf("\r\n");
}
尾插法添加元素:
void appendElement(NodePtr paraHeader, char paraChar) {
NodePtr p, q;
//1.创建一个新节点并把paraChar赋给该节点
q = (NodePtr)malloc(sizeof(LNode));
q->data = paraChar;
q->next = NULL;
//2.使p指向该链表当前的尾结点
p = paraHeader;
while (p->next != NULL) {
p = p->next;
}
//3.插入节点
p->next = q;
}
将元素插入指定位置:
void insertElement(NodePtr paraHeader, char paraChar, int paraPosition) {
NodePtr p, q;
//1.将p指向待插入位置的上一个节点
p = paraHeader;
for (int i = 0; i < paraPosition; i++) {
p = p->next;
if (p == NULL) {
printf("此位置:%d 在链表中不存在", paraPosition);
return ;
}
}
//2.创建一个新节点
q = (NodePtr)malloc(sizeof(LNode));
q->data = paraChar;
//3.插入
printf("linking\r\n");
q->next = p->next;
p->next = q;
}
在链表中删除指定元素:
void deleteElement(NodePtr paraHeader, char paraChar) {
NodePtr p, q;
//寻找指定的元素位置
p = paraHeader;
while ((p->next != NULL) && (p->next->data != paraChar)) {
p = p->next;
}
//判断指定元素是否存在
if (p->next == NULL) {
printf("该元素不存在\r\n");
return;
}
//删除指定元素
q = p->next;
p->next = p->next->next;
free(q);//释放空间
}
全部代码:
#include <stdio.h>
#include <malloc.h>
// 定义结构体链表
typedef struct LinkNode {
char data;
struct LinkNode *next;
} LNode, *LinkList, *NodePtr;
//创建链表结点
LinkList initLinkList() {
NodePtr tempHeader = (NodePtr)calloc(1, sizeof(LNode));
tempHeader->next = NULL;
return tempHeader;
}
//打印链表
void printList(NodePtr paraHeader) {
NodePtr p = paraHeader->next;
while (p != NULL) {
printf("%c", p->data);
p = p->next;
}
printf("\r\n");
}
//尾插法添加元素
void appendElement(NodePtr paraHeader, char paraChar) {
NodePtr p, q;
//1.创建一个新节点并把paraChar赋给该节点
q = (NodePtr)malloc(sizeof(LNode));
q->data = paraChar;
q->next = NULL;
//2.使p指向链表当前的尾结点
p = paraHeader;
while (p->next != NULL) {
p = p->next;
}
//3.插入节点
p->next = q;
}
//将元素插入指定位置
void insertElement(NodePtr paraHeader, char paraChar, int paraPosition) {
NodePtr p, q;
//1.将p指向待插入位置的上一个节点
p = paraHeader;
for (int i = 0; i < paraPosition; i++) {
p = p->next;
if (p == NULL) {
printf("此位置:%d 在链表中不存在", paraPosition);
return ;
}
}
//2.创建一个新节点
q = (NodePtr)malloc(sizeof(LNode));
q->data = paraChar;
//3.插入指定元素
printf("linking\r\n");
q->next = p->next;
p->next = q;
}
//从链表中删除数据
void deleteElement(NodePtr paraHeader, char paraChar) {
NodePtr p, q;
//寻找指定元素
p = paraHeader;
while ((p->next != NULL) && (p->next->data != paraChar)) {
p = p->next;
}
//判断指定元素是否存在
if (p->next == NULL) {
printf("该元素不存在\r\n");
return;
}
//删除指定元素
q = p->next;
p->next = p->next->next;
free(q);
}
//测试
void appendInsertDeleteTest() {
LinkList tempList = initLinkList();
printList(tempList);
appendElement(tempList, 'H');
appendElement(tempList, 'e');
appendElement(tempList, 'l');
appendElement(tempList, 'l');
appendElement(tempList, 'o');
appendElement(tempList, '!');
printList(tempList);
deleteElement(tempList, 'e');
deleteElement(tempList, 'a');
deleteElement(tempList, 'H');
printList(tempList);
insertElement(tempList, 'o', 1);
insertElement(tempList, 'a', 0);
printList(tempList);
}
void basicAddressTest() {
LNode tempNode1, tempNode2;
tempNode1.data = 4;
tempNode1.next = NULL;
tempNode2.data = 6;
tempNode2.next = NULL;
printf("The first node: %p, %p, %p\r\n",
&tempNode1, &tempNode1.data, &tempNode1.next);
printf("The second node: %p, %p, %p\r\n",
&tempNode2, &tempNode2.data, &tempNode2.next);
tempNode1.next = &tempNode2;
}
int main() {
appendInsertDeleteTest();
basicAddressTest();
}
运行结果:
Hello!
该元素不存在
llo!
linking
linking
alolo!
The first node: 000000000062FDE0, 000000000062FDE0, 000000000062FDE8
The second node: 000000000062FDD0, 000000000062FDD0, 000000000062FDD8