C语言链表2024.8.1

单向链表相关操作

#include <stdio.h>
#include <stdlib.h>
#include "./03_LinklistFun.h"

typedef int datatype;
typedef struct linlst
{
	union
	{
		int len;
		datatype data;
	}text;
	struct linlst* next;

}Linklist;

//创建单链表
Linklist* Create_Linklist(void)
{
	//在堆空间申请了头节点的空间,头节点的首地址存储在head指针中。
	//head指针就是头指针
	Linklist* head=(Linklist*)malloc(sizeof(Linklist));
	if(NULL == head)
	{
		printf("单链表创见失败\n");
		return NULL;
	}
	//初始化头节点中的len
	head->next = NULL;
	head->text.data=0;

	return head;
}


//头插法
void insert_linkByHead(Linklist* head,int num)
{
	//创建一个新的节点
	Linklist* temp = (Linklist*)malloc(sizeof(Linklist));
	temp->text.data=num;
	temp->next=NULL;

	//将temp头插法插入链表
	temp->next = head->next;
	head->next = temp;

	//更新头节点中链表的长度
	head->text.len++;

}
//尾插法
void insert_listByTail(Linklist* head,int num)
{
	//创建新的节点
	Linklist* temp=(Linklist*)malloc(sizeof(Linklist));
	temp->text.data=num;
	temp->next=NULL;

	//找到节点p的位置:循环判断p->next是否为NULL
	Linklist* p=head;
	p=head;
	while(p->next != NULL)
	{
		p=p->next;
	}
	//尾插法插入数据
	temp->next=p->next;
	p->next=temp;

	//更新结点中链表的长度
	head->text.len++;


}
//头删法
void del_LinkByhead(Linklist* head)
{

	Linklist* temp=	(Linklist*)malloc(sizeof(Linklist));
	//判断链表是否为空
	if(head->next == NULL)
	{
		printf("链表为空删除失败\n");
		return;
	}
	//将要释放的节点地址另存
	temp=head->next;
	head->next=temp->next;
	//释放结点
	free(temp);
	temp=NULL;

	//更新头结点链表长度
	head->text.len--;
}

//尾删法
void del_LinkBytail(Linklist* head)
{

	Linklist* p=head;
	//判断链表是否为空
	if(head->next == NULL)
	{
		printf("链表为空删除失败\n");
		return;
	}
	//循环方式找倒数2个结点p

	while(p->next->next != NULL)
	{
		p=p->next;
	}
	//释放结点
	free(p->next);
	p->next=NULL;

	//更新头结点链表长度
	head->text.len--;
}

//按位置插入
void insert_linkByIndex(Linklist* head,datatype num,int n)
{
	//判断插入位置是否合法
	if(n<1)
	{
		printf("n=%d插入位置非法\n",n);
		return;
	}
	//找要插入的位置的前一个节点位置
	//若p指向NULL,则代表插入位置非法
	Linklist* p = head;
	for(int i=0;i<n-1;i++)
	{
		p=p->next;
		if(NULL == p)
		{
			printf("插入位置非法\n");
			return;
		}
	}
	//创建一个新的节点
	Linklist* temp=(Linklist*)malloc(sizeof(Linklist));
	if(NULL == temp)
	{
		printf("创建结点失败,插入失败\n");
		return;
	}
	temp->text.data=num;
	temp->next = NULL;

	//将temp插入到p结点的后一个位置
	temp->next=p->next;
	p->next=temp;

	//更新头结点中链表的长度
	head->text.len++;
	return;



}

//按位置删除

void del_linkByIndex(Linklist* head,int n)
{
	//判断链表是否为空
	if(NULL == head->next)
	{
		printf("链表为空,按位置删除失败\n");
		return;
	}
	//判断删除位置是否合法
	if(n<1)
	{
		printf("n=%d删除位置非法\n");
		return;
	}
	//找到要删除位置的前一个结点位置
	Linklist* p = head;
	for(int i=0;i<n-1;i++)
	{
		p=p->next;
		if(NULL == p->next)
		{
			printf("删除位置非法\n");
			return;
		}
	}
	Linklist* temp=p->next;
	p->next=temp->next;
	free(temp);

	//更新结点中链表的长度
	head->text.len++;



}

//遍历链表
void show_linklist(Linklist* head)
{
	Linklist* p=head;
	while(p->next != NULL)
	{
		p=p->next;
		printf("%d\n",p->text.data);
	}
	putchar(10);

	return;

}

int main(int argc, const char *argv[])
{
	Linklist* head;
	head=Create_Linklist();
    insert_linkByIndex(head,100,1);
    insert_linkByIndex(head,200,2);
    insert_linkByIndex(head,300,3);
    insert_linkByIndex(head,800,4);
	del_linkByIndex(head,3);

//	del_LinkByhead(head);
//	del_LinkByhead(head);
//	del_LinkBytail(head);
	show_linklist(head);
	return 0;
}

单向循环链表

#include <stdio.h>
#include <stdlib.h>
#include "./03_DoubleListFun.h"

//创建单链表
Doulist* Create_Doulist(void)
{
	//在堆空间申请了头节点的空间,头节点的首地址存储在head指针中。
	//head指针就是头指针
	Doulist* head=(Doulist*)malloc(sizeof(Doulist));
	if(NULL == head)
	{
		printf("单链表创见失败\n");
		return NULL;
	}
	//初始化头节点中的len
	head->next = head;
	head->text.len=0;

	return head;
}


//头插法
void insert_linkByHead(Doulist* head,int num)
{
	//创建一个新的节点
	Doulist* temp = (Doulist*)malloc(sizeof(Doulist));
	temp->text.data=num;
	temp->next=NULL;

	//将temp头插法插入链表
	temp->next = head->next;
	head->next = temp;

	//更新头节点中链表的长度
	head->text.len++;

}
//尾插法
void insert_doulistByTail(Doulist* head,typedata num)
{
	//创建新的节点
	Doulist* temp=(Doulist*)malloc(sizeof(Doulist));
	temp->text.data=num;
	temp->next=head;

	//找到节点p的位置:循环判断p->next是否为NULL
	Doulist* p=head;
	p=head;
	while(p->next != head)
	{
		p=p->next;
	}
	//尾插法插入数据
	temp->next=p->next;
	p->next=temp;

	//更新结点中链表的长度
	head->text.len++;


}
//头删法
void del_DouByhead(Doulist* head)
{

	Doulist* temp=	(Doulist*)malloc(sizeof(Doulist));
	//判断链表是否为空
	if(head->next == head)
	{
		printf("链表为空删除失败\n");
		return;
	}
	//将要释放的节点地址另存
	temp=head->next;
	head->next=temp->next;
	//释放结点
	free(temp);
	temp=NULL;

	//更新头结点链表长度
	head->text.len--;
}

//尾删法
void del_DouBytail(Doulist* head)
{

	Doulist* p=head;
	//判断链表是否为空
	if(head->next == head)
	{
		printf("链表为空删除失败\n");
		return;
	}
	//循环方式找倒数2个结点p

	while(p->next->next != head)
	{
		p=p->next;
	}
	Doulist* temp;
	temp=p->next;
	p->next=temp->next;
	//释放结点
	free(temp);
	

	//更新头结点链表长度
	head->text.len--;
}

//按位置插入
void insert_DoulistByIndex(Doulist* head,typedata num,int n)
{
	//判断插入位置是否合法
	if(n<1)
	{
		printf("n=%d插入位置非法\n",n);
		return;
	}
	//找要插入的位置的前一个节点位置
	//若p指向NULL,则代表插入位置非法
	Doulist* p = head;
	for(int i=0;i<n-1;i++)
	{
		p=p->next;
		if(head == p->next)
		{
			printf("n=%d插入位置非法\n",n);
			return;
		}
	}
	//创建一个新的节点
	Doulist* temp=(Doulist*)malloc(sizeof(Doulist));
	if(NULL == temp)
	{
		printf("创建结点失败,插入失败\n");
		return;
	}
	temp->text.data=num;
	temp->next = NULL;

	//将temp插入到p结点的后一个位置
	temp->next=p->next;
	p->next=temp;

	//更新头结点中链表的长度
	head->text.len++;
	return;



}

//按位置删除

void del_doulistByIndex(Doulist* head,int n)
{
	//判断链表是否为空
	if(head == head->next)
	{
		printf("链表为空,按位置删除失败\n");
		return;
	}
	//判断删除位置是否合法
	if(n<1)
	{
		printf("n=%d删除位置非法\n",n);
		return;
	}
	//找到要删除位置的前一个结点位置
	Doulist* p = head;
	for(int i=0;i<n-1;i++)
	{
		p=p->next;
		if(p->next == head)
		{
			printf("n=%d删除非法\n",n);
			return;
		}
	}
	Doulist* temp=p->next;
	p->next=temp->next;
	free(temp);

	//更新结点中链表的长度
	head->text.len++;



}

//直接插入排序
void insert_linkSort(Doulist* head,typedata num)
{
	//创建一个新的节点
	Doulist* temp=(Doulist*)malloc(sizeof(Doulist));
	if(NULL == temp)
	{
		printf("创建结点失败,直接插入排序失败\n");
		return;
	}
	temp->text.data=num;
	temp->next = NULL;
	//找到要插入位置的前一个结点位置:
	//当前结点的下一个结点是否大于要插入的数据num
	Doulist* p,*q;
	p=head;
	while(p->next!=NULL)
	{
		if(num<p->next->text.data)
		{
			break;
		}
		p=p->next;
	}

    
	//将temp插入到p结点后面位置
	temp->next=p->next;
	p->next=temp;

	//更新头结点中链表的长度
	head->text.len++;
}

//链表翻转
void trainsform_list(Doulist* head)
{
	Doulist* p,*q;
	p=head->next;
	head->next=NULL;
	while(p!=NULL)
	{
		q=p->next;
		p->next=head->next;
		head->next=p;
		p=q;
	
	}

	printf("链表翻转完成\n");
}


//找中间结点:快慢指针
typedata moidNode(Doulist* head)
{
	//判断链表是否为空
	if(NULL == head->next)
	{
		printf("链表为空,没有中间结点\n");
		return (typedata)-1;
	}
	Doulist*fast,*low;
	fast=low=head->next;
	while(fast!=NULL && fast->next!=NULL)
	{
		low=low->next;
		fast=fast->next->next;
	}
	return low->text.data;

}

//释放链表
void free_linklist(Doulist** phead)
{
	//phead指向head空间
	//*phead代表访问head空间
	Doulist* temp = NULL;
	//循环头删,直到链表为空
	while((*phead)->next != NULL)
	{
		temp = (*phead)->next;
		(*phead)->next = temp->next;

		free(temp);
		(*phead)->text.len--;
	
	}
	//最后释放头结点,将头指针置为NULL
	free(*phead);
	*phead = NULL;
	return;


}

//遍历链表
void show_doulinklist(Doulist* head)
{
	Doulist* p=head;
	while(p->next != head)
	{
		p=p->next;
		printf("%d\n",p->text.data);
	}
	putchar(10);

	return;

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

向風而行

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值