单链表的实现

本文详细介绍了单链表的基本操作,包括如何创建链表、在链表中插入新节点、删除指定位置的节点、遍历链表打印所有元素、反转链表以及销毁链表。这些基本操作是链表数据结构学习的基础,对于理解和实现链表算法至关重要。
摘要由CSDN通过智能技术生成

1. 单链表定义

//1.链表的定义
typedef struct linknode
{
	data_type data;//数据域
	struct linknode *next;//指针域
}LinkNode;

2. 枚举返回值

enum res
{
	EMPTY = -5,
	POSERROR,
	MALLOCERROR,
	LINKERROR,
	LINKNULL,
	OK
};

enum op
{
	TAIL = -1,
	HEAD
};	

3. 创建单链表

//函数功能:创建一个链表
//参数:无
//返回值:链表的首地址 头结点的首地址
LinkNode *CreateLink(void)
{
	LinkNode *pHead = NULL;
	pHead = (LinkNode *)malloc(sizeof(LinkNode));
	if(NULL == pHead)
	{
		perror("malloc error");
		return NULL;
	}
	memset(pHead,0,sizeof(LinkNode));
	return pHead;
}

4. 插入新结点

分为三种情况:头部插入、中间插入、尾部插入

//函数功能:插入元素
//参数1:LinkNode * 链表的首地址
//参数2:插入的位置pos
//参数3:插入的数据元素
//返回值:成功返回OK,失败返回失败原因
int InsertItemLink(LinkNode *pHead,int pos,data_type item)
{
	//1.入参判断
	if(NULL == pHead)
	{
		return LINKNULL;
	}
	if(pos<-1)
	{
		return POSERROR;
	}
	
	//2.创建新结点
	LinkNode *pNew = NULL;
	pNew = (LinkNode *)malloc(sizeof(LinkNode));
	if(NULL == pNew)
	{
		perror("malloc error");
		return MALLOCERROR;
	}
	memset(pNew,0,sizeof(LinkNode));

	//3.将要插入的元素放入到新结点的数据域
	pNew->data = item;

	//4.定义一个游标
	LinkNode *pTmp = NULL;
	pTmp = pHead;
	int i=0;
	switch(pos)
	{
		case HEAD://头部插入
			{
				//先保护好要插入结点后面的结点地址
				pNew->next = pHead->next;
				//进行插入
				pHead->next = pNew;
			}
			break;
		case TAIL://尾部插入
			{
				//移动游标到尾结点
				while(pTmp->next!=NULL)
				{
					pTmp = pTmp->next;
				}
				//将新结点进行插入
				pTmp->next = pNew;
			}
			break;
		default://中间插入
			{
				//移动游标到插入的位置的前一个位置
				while((i<=pos-1)&&(pTmp!=NULL))
				{
					pTmp = pTmp->next;
					i++;
				}
				//先保护好要插入结点后面的结点地址
				pNew->next = pTmp->next;
				//进行插入
				pTmp->next = pNew;
			}
	}
	return OK;	
}

5. 删除结点

//函数功能:删除元素
//参数1:LinkNode * 链表的首地址
//参数2:删除的位置
//参数3:删除的元素保存在*pData
//返回值:成功返回OK,失败返回失败原因
int DeleteItemLink(LinkNode *pHead,int pos,data_type *pData)
{
	//1.入参判断
	if(NULL == pHead)
	{
		return MALLOCERROR;
	}
	if(pos<-1)
	{
		return POSERROR;
	}

	//2.游标定义
	LinkNode *pTmp = NULL;
	LinkNode *pDel = NULL;
	pTmp = pHead;
	pDel = pHead->next;
	switch(pos)
	{
		case HEAD:
			*pData = pDel->data;
			pTmp->next = pDel->next;
			free(pDel);
			pDel = NULL;
			break;
		case TAIL:
			while(pDel->next!=NULL)
			{
				pTmp = pDel;
				pDel = pDel->next;
			}
			free(pDel);
			pDel = NULL;
			pTmp->next = NULL;
			break;
		default://中间删除
			//找到要删除的位置
			//pTmp指向要删除结点的前一个位置
			//pDel指向要删除的结点
			for(int i=0;i<=pos-1;i++)
			{
				pTmp = pDel;
				pDel = pDel->next;
			}
			//把要删除的数据保留
			*pData = pDel->data;
			//删除 
			pTmp->next = pDel->next;
			//释放结点
			free(pDel);
			pDel = NULL;
	}
	return OK;
}

6. 遍历单链表

//函数功能:遍历单链表
//参数:链表首地址
//返回值:成功返回OK,失败返回失败原因
int  ShowLink(LinkNode *pHead)
{
	//1.入参判断
	if(NULL == pHead)
	{
		return MALLOCERROR;
	}

	//2.定义一个游标,指向首结点
	LinkNode *pTmp = NULL;
	pTmp = pHead->next;

	while(pTmp!=NULL)
	{
		printf("%d ",pTmp->data);
		pTmp = pTmp->next;
	}
	printf("\n");
	return OK;
}

7. 反转

//函数功能:反转单链表内容
//参数:头结点地址
//返回值:成功返回OK,失败返回失败原因
int Reverse(LinkNode *pHead)
{
	//1.入参判断
	if(NULL == pHead)
	{
		return LINKNULL;
	}

	//2.定义游标并剪短头结点
	LinkNode *pFirst = NULL;
	LinkNode *pTmp = NULL;
	pFirst = pHead->next;
	pHead->next = NULL;

	while(1)
	{
		pTmp = pFirst;
		if(pTmp==NULL)
		{
			break;
		}
		pFirst = pFirst->next;

		//插入
		pTmp->next = pHead->next;
		pHead->next = pTmp;
	}
	return OK;
}

8. 销毁单链表

//函数功能:销毁单链表
//参数:二级指针
//返回值:成功返回OK,失败返回失败原因
int DestroyLink(LinkNode **pHead)
{
	//1.入参判断
	if(*pHead == NULL)
	{
		return LINKNULL;
	}
	while(1)
	{
		LinkNode *pTmp = NULL;
		pTmp = (*pHead)->next;
		if(pTmp==NULL)
		{
			break;
		}
		(*pHead)->next = pTmp->next;
		free(pTmp);
		pTmp = NULL;
	}
	free(*pHead);
	*pHead = NULL;
	return OK;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值