带头双向循环链表

先定义一个结构体

#include<iostream> 
#include<cassert>
using namespace std;
typedef int ElementDate;

 typedef struct ListNode
{
	ElementDate date;
	struct ListNode* next;//指向下一个
	struct ListNode* prev;//指向前一个
}ListNode;

初始化

ListNode* ListInit()
{
	ListNode* phead = (ListNode*)malloc(sizeof(ListNode));//哨兵位
	phead->next = phead;
	phead->prev = phead;
	return phead;
}

查找功能,返回的是节点指针,给下面的指定位置增删服务

ListNode* ListFind(ListNode* phead,ElementDate x) 
{
	assert(phead);
	ListNode* cur = phead->next;
	while (cur != phead)
	{
		if (cur->date == x)
			return cur;
		else cur = cur->next;
	}
	return NULL;
}

申请一个新节点

ListNode* buyListNode(ElementDate x)
{
	ListNode* phead = (ListNode*)malloc(sizeof(ListNode));
	phead->date = x;
	phead->next = NULL;
	phead->prev = NULL;
	return phead;
}

尾插

void ListPushBack(ListNode* phead, ElementDate x)
{//改变结构体不需要二级指针
	//或者直接ListInsert(phead, x);
	assert(phead);
	ListNode* tail = phead->prev;//尾节点
	ListNode* newnode = buyListNode(x);
	tail->next = newnode;
	newnode->prev = tail;
	phead->prev = newnode;
	newnode->next = phead;
}

尾删

void ListPopBack(ListNode* phead)
{
	assert(phead);
	if (phead->next == phead)return;
	//assert(phead->next!=phead);
	ListNode* tail = phead->prev;
	ListNode* prevtail = tail->prev;
	prevtail->next = phead;
	phead->prev = prevtail;
	free(tail); 
}

头插

void ListPushFront(ListNode* phead, ElementDate x)
{
	//或ListInsert(phead->next, x);
	assert(phead);
	ListNode* newnode = buyListNode(x);
	ListNode* next = phead->next;
	phead->next = newnode;
	newnode->prev = phead;
	newnode->next = next;
	next->prev = newnode;
}

头删

void ListPopFront(ListNode* phead)
{
	assert(phead);
	assert(phead->next != phead); 
	ListNode* head = phead->next;
	phead->next = head->next;
	head->prev = phead;
	free(head);
}

指定位置前插入,前面的尾插,头插都可以调用这个简单很多

void ListInsert(ListNode* pos, ElementDate x)//pos之前插入
{
	assert(pos);
	ListNode* newnode = buyListNode(x);
	ListNode* pospre = pos->prev;
	pos->prev = newnode;
	newnode->next = pos;
	newnode->prev = pospre;
	pospre->next = newnode;
}

指定位置删除,形参是一个节点的指针,前面头删尾删可以用

void ListErase(ListNode* pos)//删除pos
{
	assert(pos);
	ListNode* pospre = pos->prev;
	pospre->next = pos->next;
	pos->next->prev = pospre;
	free(pos);
}

清空链表

void ListDestroy(ListNode* phead)
{
	assert(phead);
	ListNode* cur = phead->next;
	ListNode* next = cur;
	while (next != phead)
	{
		cur = cur->next;
		free(next);
		next = cur;
	}
	//一级指针不能改变形参,在外面置空 free(phead);
	phead = NULL; 
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值