数据结构之不带头结点的单链表

不带头结点的单链表和带头结点的单链表

和带有头结点的单链表相比,不带头结点的单链表显得更直观。但不带头结点的单链表在插入和删除第 1 个元素时与插入和删除其它元素时的操作不一样,在创建链表时也不一样,要改变链表头指针的值。而带有头点的单链表无论插入和删除第几个元素,其操作都是统一的。

对插入和删除参数传递存在问题,以及对程序运行后出现的乱码存在问题

数据结构之带头结点和不带头结点单链表存在的问题

不带头结点链表实现

#include<stdio.h>
#include<malloc.h>
#include<stdlib.h>
#define Destroy Clear	//Destroy和Clear操作是一样的

//和设头结点的单链表在定义存储结构上是相同的
typedef struct Node
{
	int data;	//数据域
	struct Node *next;	//指针域
}NODE,*PNODE;

//基本操作
PNODE Create1();	//创建无头结点的单链表,在表头插入数据
PNODE Create2();	//创建无头结点的单链表,在表尾插入数据
void Clear(PNODE pHead);//置空或销毁单链表,
bool Empty(PNODE pHead);//判断单链表是否为空
int	Length(PNODE pHead);//返回单链表中元素的个数
bool Get(PNODE pHead,int i,int *e);//将第i个元素的值赋给e
bool Prior(PNODE pHead,int cur_e,int *pre_e);//求cur_e的前驱元素,用pre_e保存
bool Next(PNODE pHead,int cur_e,int *next_e);//求cur_e的后继元素,用next_e保存
bool Insert(PNODE *pHead,int i,int e);//在第i个元素前面插入元素e
bool Delete(PNODE *pHead,int i,int *e);//删除单链表第i个元素,并用e保存
void Traverse(PNODE pHead);//遍历单链表
void Sort(PNODE pHead);//排序

int main()
{
	int val;
	PNODE pHead=Create1();
	printf("初始化链表中的元素为:");
	Traverse(pHead);
	Get(pHead,3,&val);
	printf("第3个元素的值为:%d\n",val);
	Insert(&pHead,6,100);
	printf("插入第六个元素后:");
	Traverse(pHead);
	Clear(pHead);
	Traverse(pHead);
	return 0;
}
PNODE Create1()
{
	//在表头插入数据
	int i,n;
	PNODE pHead=NULL,pNew;
	printf("请输入数据元素的个数:");
	scanf("%d",&n);
	if(n<1)
		exit(-1);
	pHead=(PNODE)malloc(sizeof(NODE));//生成一个首结点
	if(NULL==pHead)
		exit(-1);
	printf("请输入第1个元素的值:");
	scanf("%d",&pHead->data);
	pHead->next=NULL;
	for(i=0;i<n-1;i++)
	{
		pNew=(PNODE)malloc(sizeof(NODE));
		if(NULL==pNew)
			exit(-1);
		printf("请输入第%d个元素的值:",i+2);
		scanf("%d",&pNew->data);
		pNew->next=pHead;
		pHead=pNew;
	}
	return pHead;
}
PNODE Create2()
{
	//在表尾插入数据
	int i,n;
	PNODE pHead=NULL,pNew,pTail;
	printf("请输入数据元素的个数:");
	scanf("%d",&n);
	if(n<1)
		exit(-1);
	pHead=(PNODE)malloc(sizeof(NODE));//生成一个首结点
	if(NULL==pHead)
		exit(-1);
	printf("请输入第1个元素的值:");
	scanf("%d",&pHead->data);
	pHead->next=NULL;
	pTail=pHead;
	for(i=0;i<n-1;i++)
	{
		pNew=(PNODE)malloc(sizeof(NODE));
		if(NULL==pNew)
			exit(-1);
		printf("请输入第%d个元素的值:",i+2);
		scanf("%d",&pNew->data);
		pNew->next=pTail->next;
		pTail->next=pNew;
		pTail=pNew;
	}
	return pHead;
}
void Clear(PNODE pHead)
{
	PNODE p=pHead;
	while(p!=NULL)
	{
		p=pHead->next;
		free(pHead);
		pHead=p;
	}
}
bool Empty(PNODE pHead)
{
	if(pHead==NULL)
		return true;
	else
		return false;
}
int Length(PNODE pHead)
{
	int count=0;//存放链表元素个数
	PNODE p=pHead;
	while(p!=NULL)
	{
		count++;
		p=p->next;
	}
	return count;
}
bool Get(PNODE pHead,int i,int *e)
{
	int j=1;
	PNODE p=pHead;
	while(p!=NULL&&j<i)//找到第i位置
	{
		j++;
		p=p->next;
	}
	if(j>i||p==NULL)//判断i的值是否合理
		return false;
	*e=p->data;
	return true;
}
bool Prior(PNODE pHead,int cur_e,int *pre_e)
{
	PNODE p=pHead,q;
	while(p->next!=NULL)
	{
		q=p->next;
		if(cur_e==q->data)
		{
			*pre_e=p->data;
			return true;
		}
		p=q;
	}
	return false;
}
bool Next(PNODE pHead,int cur_e,int *next_e)
{
	PNODE p=pHead;
	while(p->next!=NULL)
	{
		if(cur_e==p->data)
		{
			*next_e=p->next->data;
			return true;
		}
		p=p->next;
	}
	return false;
}
bool Insert(PNODE *pHead,int i,int e)
{
	//在不带头结点的单链表第i个位置之前插入元素e
	int j=1;
	PNODE p=*pHead,pNew;
	if(i<1)
		return false;
	pNew=(PNODE)malloc(sizeof(NODE));
	pNew->data=e;
	if(i==1)
	{
		pNew->next=*pHead;
		*pHead=pNew;
	}
	else
	{
		while(p!=NULL&&j<i-1)
		{
			p=p->next;
			j++;
		}
		if(p==NULL)
			return false;
		pNew->next=p->next;
		p->next=pNew;
	}
}
bool Delete(PNODE *pHead,int i,int *e)
{
	int j=1;
	PNODE p=*pHead,q;
	if(i<1)
		return false;
	if(i==1)
	{
		*pHead=p->next;
		*e=p->data;
		free(p);
	}
	else
	{
		while(j<i-1&&p->next!=NULL)
		{
			j++;
			p=p->next;
		}
		if(p->next==NULL)
			return false;
		
		q=p->next;
		*e=q->data;
		p->next=q->next;
		free(q);
	}
}
void Traverse(PNODE pHead)
{
	PNODE p=pHead;
	while(p!=NULL)
	{
		printf("%d ",p->data);
		p=p->next;
	}
	printf("\n");
}

猜你喜欢

转载自blog.csdn.net/qq_42447402/article/details/85699495