定义链表
一般先定义结构体
结构体内包含数据域和指针域
struct student
{
long num;
float score;
struct student * next;
};
链表结点大小
用于后面动态内存申请
#define LEN sizeof(struct student)
结点数
全局变量
int n = 0;
创建链表
struct student * creat()
{
struct student * head; // 头指针
struct student * p1, * p2; // 移动指针
n = 0; // 结点个数
p1 = p2 = (struct student *)malloc(LEN); // 申请内存
scanf("%ld,%f", &p1->num, &p1->score); // 输入数据
head = NULL; // 头指针指向NULL
while (p1->num != 0) // 存储数据(输入0结束)
{
n = n + 1; // 结点数加一
if (n == 1) // 如果是第一个结点
head = p1; // 头指针指向第一个结点
else // 读到第一个以后结点
p2->next = p1; // 前一个结点指向当前结点
p2 = p1; // 把当前结点赋给p2,下一步p1指向新开辟的结点
p1 = (struct student *)malloc(LEN); // 开辟下一个新结点
scanf("%ld,%f", &p1->num, &p1->score); // 继续输入
}
p2->next = NULL; // 最后个结点指向NULL
return(head); // 返回头指针
}
删除结点
struct student * del(struct student * head, long num)
{
struct student * p1, *p2;
if (head == NULL) // 如果是空表
{
printf("\nlist null!\n");
return head;
}
p1 = head; // p1指向第一个结点
while (num != p1->num && p1->next != NULL) // 开始搜索,直到到达链表尾
{
p2 = p1;
p1 = p1->next; // p2指向上一个结点,防止其丢失。 p1指向下一个结点,继续搜索
}
if (num == p1->num) // 找到了
{
if (p1 == head) // 如果找到的是第一个结点,则删除头结点
head = p1->next; // 将头结点指向第二个结点,丢弃第一个结点
else
p2->next = p1->next; // 丢弃p1这个结点:其之前的结点(即p2)指向p1之后一个结点
printf("delete: %ld\b", num);
n = n - 1; // 结点数-1
}
else // 没有找到
printf("%ld not benn found!\n", num);
return head; // 返回头结点
}
插入结点
struct student * insert(struct student * head, struct student * stud) // 参数:链表头结点, 需要插入的结点
{
struct student * p0, * p1, *p2; // 移动指针
p1 = head; // p1指向第一个结点
p0 = stud; // p0指向新结点
if (head == NULL) // 如果是空链表,则将这个结点作为第一个结点
{
head = p0;
p0->next = NULL;
}
else // 非空链表
{
while ((p0->num > p1->num) && (p1->next != NULL)) // 还没到达结点位置或没到达链尾
{
p2 = p1; // 保存当前结点
p1 = p1->next; // 继续搜索下一个结点
}
if (p0->num <= p1->num) // 找到了
{
if (p1 == head) // 插入到第一个结点之前
head = p0;
else
p2->next = p0; // 插入p1之前,p2之后
p0->next = p1; // p0(新结点)指向p1
}
else // 没找到(就是插到尾结点之后)
{
p1->next = p0;
p0->next = NULL;
}
}
n = n + 1; // 结点数+1
return head; // 返回头结点
}
打印链表
void print(struct student * head)
{
struct student * p; // 移动指针
// printf("There are the linked list:\n");
p = head; // 将头指针赋值给移动结点
if (p != NULL) // 非空表
{
do
{
printf("%ld %5.1f\n", p->num, p->score);
p = p->next; // 指向下一个结点
}while (p != NULL); // 未到达链表尾
}
}
释放(清空)链表
void disposal_LinkList(struct Student * headNode)
{
struct Student * nextNode; // 下一个结点
struct Student * curNode; // 当前结点
if (headNode == NULL) // 如果为空表
{
return;
}
//清空链表,是不清空头节点的,因此从第一个有数据的节点开始释放
curNode = headNode->next; // 当前结点指向第一个结点
while (curNode != NULL) // 未到达链表尾,继续释放
{
nextNode = curNode->next; //先存下下一个节点的位置
free(curNode); // 释放当前结点
curNode = nextNode; // 当前结点指向下一个结点
}
free(headNode); //释放头结点
headNode = NULL; //头结点指针置空
}