数据结构:双向链表 增删改查

双向链表的基本操作:

        包含三个文件:

                1.c为函数的实现

                1.h为函数的声明

                main.c为主函数

        由于查找和跟前面三个类似,故没有实现

测试结果以及部分说明如下

                1、头插法建立链表说明以及测试结果:

                

                  2、尾插法建立链表说明以及测试结果:

 

                        3、在index位置插入

  

                        4、修改index位置值

 

 

                        5、删除index位置

  

代码如下

1.c文件

/*************************************************************************
 > File Name   : 1.c
 > Author      : 潘潘的嵌入式
 > Function    : 函数实现
 > Created Time: 2023年01月07日 星期六 09时41分35秒
 ************************************************************************/

#include "1.h"
//带头节点双向链表的初始化(建立一个双向循环链表)
node_t *init_list()
{
	//从堆开辟空间
	node_t *head = (node_t*)malloc(sizeof(node_t));
	//检测是否成功
	SYSERR(NULL,==,head,"malloc is error",NULL);
	//初始化参数
	head -> data = 0;
	head -> next = NULL;
	head -> pion = NULL;
	return head;
}
//从堆开辟结点
node_t *creat_node(ElemType data)
{
	node_t *newNode = (node_t*)malloc(sizeof(node_t));
	SYSERR(NULL,==,newNode,"newNode is null",NULL);
	newNode -> data = data;
	newNode -> next = NULL;
	newNode -> pion = NULL;
	return newNode;
}
//带头结点 头插法 建立链表
int insert_hlist(node_t *head,ElemType data)
{
	//检测参数合法性
	SYSERR(NULL,==,head,"head is NULL",-1);
	node_t *newNode = creat_node(data);
	//检测是否开辟成功
	SYSERR(NULL,==,newNode,"newNode is null",-2);
	//将新节点插入链表
	if(NULL == head -> next)//链表中只有头结点
	{
		head -> next = newNode;
		newNode -> pion = head;
		newNode -> next = NULL;
	}
	else
	{
		newNode -> next = head -> next;
		newNode -> pion = head;
		head -> next -> pion = newNode;
		head -> next = newNode;
	}
	return 0;
}
//带头节点尾插法建立链表
int insert_tlist(node_t *head,ElemType data)
{
	//检测参数合法性
	SYSERR(NULL,==,head,"head is null",-1);
	node_t *newNode = creat_node(data);
	//检测是否开辟成功
	SYSERR(NULL,==,newNode,"newNode is null",-2);
	//找到最后一个结点
	node_t *p = head;
	while(NULL != p -> next)
	{
		p = p -> next;
	}
	//将新节点插入链表
	newNode -> next = p -> next;
	newNode -> pion = p;
	p -> next = newNode;
	return 0;
}
//在index位置插入一个结点
int insert_index(node_t *head,int index,ElemType data)
{
	//检测参数合法性
	SYSERR(NULL,==,head,"head is null",-1);
	if(index <= 0)
	{
		printf("位置不合法\n");
		return -3;
	}
	node_t *newNode = creat_node(data);
	//检测是否开辟成功
	SYSERR(NULL,==,newNode,"newNode is null",-2);
	int i = 0;
	node_t *p = head;
	//找到要插入结点的前一个位置
	while(NULL != p && i < index - 1)
	{
		++i;
		p = p -> next;
	}
	//根据循环跳出的情况进行插入
	if( NULL == p)
	{
		printf("位置不合法\n");
		return -3;
	}
	else if(NULL == p -> next)//p为最后一个结点
	{
		newNode -> next = p -> next;
		newNode -> pion = p;
		p -> next = newNode;	
	}
	else//p为中间结点
	{
		newNode -> next = p -> next;
		newNode -> pion = p;
		p -> next -> pion = newNode;
		p -> next = newNode;
	}
	return 0;
}
//修改index位置值为data
int revise_index(node_t *head,int index,ElemType data)
{
	//检测参数合法性
	SYSERR(NULL,==,head,"head is null",-1);
	if(index <= 0)
	{
		printf("位置不合法\n");
		return -3;
	}
	node_t *newNode = creat_node(data);
	//检测是否开辟成功
	SYSERR(NULL,==,newNode,"newNode is null",-2);
	
	int i = 0;
	node_t *p = head;
	//找到index位置
	while(p != NULL && i < index)
	{
		++i;
		p = p -> next;
	}
	if(NULL == p)
	{
		printf("位置不合法\n");
		return -3;
	}
	else
	{
		p -> data = data;
	}
	return 0;
}
//删除第index个元素
int delete_index(node_t *head,int index)
{
	//检测参数合法性
	SYSERR(NULL,==,head,"head is null",-1);
	if(index <= 0)
	{
		printf("位置不合法\n");
		return -3;
	}
	//找到index前一个位置
	int i = 0;
	node_t *p = head;
	node_t *q;
	while(p != NULL && i < index -1)
	{
		++i;
		p = p -> next;
	}	
	//根据循环跳出的情况进行插入
	if( NULL == p || NULL == p -> next)
	{
		printf("位置不合法\n");
		return -3;
	}
	else if(NULL == p -> next -> next)//index为最后个结点
	{	
		q = p -> next;
		q -> pion = NULL;
		p -> next = q -> next;
		free(q);		
	}
	else//index为中间结点
	{
		q = p -> next;
		p -> next = q -> next;
		q -> next -> pion = p;
		free(q);	
	}
	return 0;
}
//查找data的位置

//查找index位置的值

//打印双向链表
void show_list(node_t *head)
{
	//参数合法性检测
	SYSERR(NULL,==,head,"head is null",);
	node_t *p = head -> next;
	printf("data ");
	while(NULL != p)
	{
		printf("%d ",p->data);
		p = p -> next;
	}
	printf("\n");
}


1.h文件

/*************************************************************************
 > File Name   : 1.h
 > Author      : 潘潘的嵌入式
 > Function    : 函数定义和声明
 > Created Time: 2023年01月07日 星期六 09时41分54秒
 ************************************************************************/

#ifndef __1_H
#define __1_H
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<unistd.h>

//功能:安全检测宏
//@x:要检查的变量 @opt:操作符 @y:要检查的变量 @mes:报错信息 @z:返回值
#define SYSERR(x,opt,y,mes,z) if(x opt y)		     \
							  {				         \
							  		printf("%s %d %s : error %s",__FILE__,__LINE__,__func__,mes);		\
							  		return z;		 \
							  }
//双向链表
//结构体变量
typedef int ElemType; //所需要的数据类型
typedef struct node
{
	ElemType data; //数据
	struct node *next;//后继指针
	struct node *pion;//前驱指针
}node_t;//node_t是结构体变量 node_t *是结构体指针

//功能:带头结点双向链表的初始化(建立一个双向循环链表)
//返回值:结构体指针
node_t *init_list();

//功能:从堆开辟结点
//参数:@data:数据域
//返回值:结构体指针
node_t *creat_node(ElemType data);

//功能:带头结点 头插法 建立链表
//参数:@head:链表头结点 @data:数据域
//返回值:0:成功 非0:失败
int insert_hlist(node_t *head,ElemType data);

//功能:带头结点 尾插法 建立链表
//参数:@head:链表头结点
//返回值:0:成功 非0:失败
int insert_tlist(node_t *head,ElemType data);

//功能:在index位置插入一个结点
//参数:@head:链表头结点 @index:要插入的位置 @data:要插入的值
//返回值:0:成功 非0:失败
int insert_index(node_t *head,int index,ElemType data);

//功能:修改index位置值为data
//参数:@head:链表头结点 @index:要修改的位置 @data:要修改的值
//返回值:0:成功 非0:失败
int revise_index(node_t *head,int index,ElemType data);

//功能:删除第index个元素
//参数:@head:链表头结点 @index:要删除的位置
//返回值:0:成功 非0:失败
int delete_index(node_t *head,int index);

//功能:打印双向链表
//参数:@head:链表头结点
void show_list(node_t *head);



#endif

main.c文件

/*************************************************************************
 > File Name   : main.c
 > Author      : 潘潘的嵌入式
 > Function    : 主函数
 > Created Time: 2023年01月07日 星期六 09时42分14秒
 ************************************************************************/


#include "1.h"

int main(int argc, char* argv[])
{
	//创建双向链表
	node_t *head = init_list();
	//检测是否创建成功 
	SYSERR(NULL,==,head,"head is null",-1);
	//打印head内容 以及地址
	printf("head = %p head->data = %d head->next = %p head->pion = %p\n",head,head->data,head->next,head->pion);
	
	
#if 0
	//头插法测试
	ElemType a[10] = {1,3,5,7,9,2,4,6,8,10};
	for(int i = 0; i < 10; i++)
	{
		insert_hlist(head,a[i]);
	}
	show_list(head);
#endif
	
#if 1
	//尾插法测试
	ElemType a[10] = {1,3,5,7,9,2,4,6,8,10};
	for(int i = 0; i < 10; i++)
	{
		insert_tlist(head,a[i]);
	}
	show_list(head);
#endif
	
#if 0
	//在index位置插入测试
	int index;
	ElemType data;
	printf("请输入你要插入的位置和数据:\n");
	scanf("%d %d",&index,&data);
	int res = insert_index(head,index,data);
	if(!res)
	{
		printf("插入成功\n");
		show_list(head);
	}
	else
	{
		printf("插入失败\n");
	}
#endif

#if 0
	//修改index位置值测试
	int index;
	ElemType data;
	printf("请输入你要修改的位置和数据:\n");
	scanf("%d %d",&index,&data);
	int res = revise_index(head,index,data);
	if(!res)
	{
		printf("修改成功\n");
		show_list(head);
	}
	else
	{
		printf("修改失败\n");
	}
#endif
	
#if 1
	//删除index位置值测试
	int index;
	printf("请输入你要删除的位置:\n");
	scanf("%d",&index);
	int res = delete_index(head,index);
	if(!res)
	{
		printf("删除成功\n");
		show_list(head);
	}
	else
	{
		printf("删除失败\n");
	}
#endif
	return 0;
}

说明:如有错误,请及时指出。共同学习,共同进步

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值