什么是链表
关于链表,百度百科 中有如下定义
链表是一种物理存储单元上非连续、非顺序的存储结构,数据元素的逻辑顺序是通过链表中的指针链接次序实现的。链表由一系列结点(链表中每一个元素称为结点)组成,结点可以在运行时动态生成。每个结点包括两个部分:一个是存储数据元素的数据域,另一个是存储下一个结点地址的指针域。
链表的优点
使用链表结构可以克服数组链表需要预先知道数据大小的缺点,链表结构可以充分利用计算机内存空间,实现灵活的内存动态管理。
链表的实现
实验编程
下面通过C语言实现单链表的 创建,头部插入,尾部插入,随意位置插入,移除结点,链表销毁,链表遍历功能
linklist.h
#ifndef _LINK_LIST_H_
#define _LINK_LIST_H_
#include <stdbool.h>
/* 定义结点 */
struct node
{
int data;
struct node* pNext;
};
/*
* 函数名称:creat_node
* 功能描述:创建结点
* 返 回 值:结点指针
*/
struct node* creat_node(void);
/*
* 函数名称:insert_node_from_head
* 功能描述:从头部插入结点
* 输入参数:pHead-链表头指针,data-要插入的值
* 返 回 值:true-成功,false-失败
*/
bool insert_node_from_head(struct node* pHead, int data);
/*
* 函数名称:insert_node_from_tail
* 功能描述:从尾部插入结点
* 输入参数:pHead-链表头指针,data-要插入的值
* 返 回 值:true-成功,false-失败
*/
bool insert_node_from_tail(struct node* pHead, int data);
/*
* 函数名称:insert_node_to_specified_location
* 功能描述:从指定位置插入结点
* 输入参数:pHead-链表头指针,loacation-要插入的位置,data-要插入的值
* 返 回 值:true-成功,false-失败
*/
bool insert_node_to_specified_location(struct node* pHead, int loacation, int data);
/*
* 函数名称:remove_node
* 功能描述:移除某个结点
* 输入参数:pHead-链表头指针,data-删除结点对应的数据
* 返 回 值:true-成功,false-失败
*/
bool remove_node(struct node* pHead, int data);
/*
* 函数名称:linklist_print
* 功能描述:遍历链表
* 输入参数:pHead-链表头指针
* 返 回 值:无
*/
void linklist_print(struct node* pHead);
/*
* 函数名称:destroy_linklist
* 功能描述:销毁链表
* 输入参数:pHead-链表头指针
* 返 回 值:无
*/
void destroy_linklist(struct node* pHead);
#endif
linklist.c
```#include "link_list.h"
#include <stdlib.h>
#include <stdio.h>
/*
* 函数名称:creat_node
* 功能描述:创建结点
* 返 回 值:结点指针
*/
struct node* creat_node(void)
{
struct node* pNode = (struct node*)malloc(sizeof(struct node));
if (pNode != NULL)
{
pNode->data = 0;
pNode->pNext = NULL;
return pNode;
}
return NULL;
}
/*
* 函数名称:insert_node_from_head
* 功能描述:从头部插入结点
* 输入参数:pHead-链表头指针,data-要插入的值
* 返 回 值:true-成功,false-失败
*/
bool insert_node_from_head(struct node* pHead, int data)
{
struct node* pTmp = creat_node();
if (pTmp == NULL)
return false;
pTmp->data = data;
pTmp->pNext = pHead->pNext;
pHead->pNext = pTmp;
return true;
}
/*
* 函数名称:insert_node_from_tail
* 功能描述:从尾部插入结点
* 输入参数:pHead-链表头指针,data-要插入的值
* 返 回 值:true-成功,false-失败
*/
bool insert_node_from_tail(struct node* pHead, int data)
{
struct node* pTmp = pHead;
struct node* pAdd = creat_node();
if (pAdd == NULL)
return false;
pAdd->data = data;
pAdd->pNext = NULL;
while (pTmp->pNext != NULL)
{
pTmp = pTmp->pNext;
}
pTmp->pNext = pAdd;
return true;
}
/*
* 函数名称:insert_node_to_specified_location
* 功能描述:从指定位置插入结点
* 输入参数:pHead-链表头指针,loacation-要插入的位置,data-要插入的值
* 返 回 值:true-成功,false-失败
*/
bool insert_node_to_specified_location(struct node* pHead, int loacation, int data)
{
int i;
struct node* pTmp = pHead;
struct node* pAdd = creat_node();
if (pAdd == NULL)
return false;
pAdd->data = data;
pAdd->pNext = NULL;
struct node* p = NULL;
for (i = 0; i < loacation; i++)
{
pTmp = pTmp->pNext;
}
p = pTmp->pNext;
pTmp->pNext = pAdd;
pAdd->pNext = p;
return true;
}
/*
* 函数名称:remove_node
* 功能描述:移除某个结点
* 输入参数:pHead-链表头指针,data-删除结点对应的数据
* 返 回 值:true-成功,false-失败
*/
bool remove_node(struct node* pHead, int data)
{
struct node* pTmp = pHead;
struct node* p = creat_node();
if (p == NULL)
return false;
while (pTmp->pNext != NULL)
{
p = pTmp;
pTmp = pTmp->pNext;
if (pTmp->data == data)
{
p->pNext = pTmp->pNext;
free(pTmp);
return true;
}
}
return false;
}
/*
* 函数名称:linklist_print
* 功能描述:遍历链表
* 输入参数:pHead-链表头指针
* 返 回 值:无
*/
void linklist_print(struct node* pHead)
{
struct node* pTmp = pHead->pNext;
printf("linklist: ");
while (pTmp->pNext != NULL)
{
printf("%d ", pTmp->data);
pTmp = pTmp->pNext;
}
printf("%d", pTmp->data);
printf("\r\n");
}
/*
* 函数名称:destroy_linklist
* 功能描述:销毁链表
* 输入参数:pHead-链表头指针
* 返 回 值:无
*/
void destroy_linklist(struct node* pHead)
{
struct node* pTmp, * pDel;
pTmp = pHead;
while (pTmp->pNext != NULL)
{
pDel = pTmp;
free(pDel);
pDel = NULL;
pTmp = pTmp->pNext;
}
}
main.c
#include <stdio.h>
#include "link_list.h"
int main(void)
{
/* 创建链表头 */
struct node* pListHeader = creat_node();
if (pListHeader == NULL)
return -1;
printf("尾部插入\n");
/* 插入数据 */
int i = 0;
for (i = 0; i < 10; i++)
insert_node_from_tail(pListHeader, i + 1);
linklist_print(pListHeader);
printf("删除数据为5的结点\n");
remove_node(pListHeader, 5);
linklist_print(pListHeader);
printf("\r\n");
struct node* p = creat_node();
printf("头部插入\n");
for (i = 0; i < 10; i++)
insert_node_from_head(p, i + 1);
linklist_print(p);
printf("\r\n");
printf("在第5个位置插入数据为8的结点\n");
insert_node_to_specified_location(p, 5, 8);
linklist_print(p);
destroy_linklist(pListHeader);
destroy_linklist(p);
return 0;
}
运行结果:

1700

被折叠的 条评论
为什么被折叠?



