C 双向循环链表:创建、插入、遍历、求长、查找、删除、排序、销毁

知识共享许可协议 版权声明:署名,允许他人基于本文进行创作,且必须基于与原先许可协议相同的许可协议分发本文 (Creative Commons

C 双向循环链表:创建、插入、遍历、求长、查找、删除、排序、销毁

一、双向循环链表存在的意义

数组这样的结构提供了连续内存的访问和使用,链表是对内存零碎空间的有效组织和使用,双向循环链表增大了访问的自由度。

二、节点的定义

typedef struct node
{
	int data;
	struct node *pre;
	struct node *next;
}Node;

三、实现

单向链表掌握了,双向循环链表学起来就很容易了。

1.创建(即创建一个空链表)
Node * createList()
{
	Node * head = (Node *)malloc(sizeof(Node));
	if (NULL == head)
		exit(-1);
	head->pre = head;
	head->next = head;
	return head;
}

在这里插入图片描述

2.插入(头插法)
void insertList(Node* head,int input)
{
	Node * ptr = (Node *)malloc(sizeof(Node));
	if (NULL == ptr)
		exit(-1);
	ptr->data = input;
	ptr->next = head->next;
	ptr->pre = head;
	head->next = ptr;
	ptr->next->pre = ptr;
}

在这里插入图片描述

3.遍历

正向和反向都可以

void traverseNList(Node* head)
{
	Node* tmp = head->next;
	while (tmp != head)
	{
		printf("%-3d", tmp->data);
		tmp = tmp->next;
	}
}
void traversePList(Node* head)
{
	Node* tmp = head->pre;
	while (tmp != head)
	{
		printf("%-3d", tmp->data);
		tmp = tmp->pre;
	}
}
4.求长
int lengthList(Node* head)
{
	int len = 0;
	Node* tmp = head->next;
	while (tmp != head)
	{
		len++;
		tmp = tmp->next;
	}
	return len;
}
5.查找
Node * findDataList(Node* head, int findData)
{
	Node* fnext=head->next, *fpre = head->pre;
	while (fpre != fnext->pre)
	{
		if (findData == fnext->data)
			return fnext;
		if (findData == fpre->data)
			return fpre;
		if (fnext == fpre)
			break;
		fnext = fnext->next;
		fpre = fpre->pre;
	}
	return NULL;
}

下面分析找不到结束查找的情况:
①查找的链表节点为偶数个:
在这里插入图片描述
②查找的链表节点为奇数个:
在这里插入图片描述

6.删除
void deleteDataList(Node *pfind)
{
	pfind->pre->next = pfind->next;
	pfind->next->pre = pfind->pre;
	free(pfind);
}

在这里插入图片描述

7.排序

冒泡排序

void sortList(Node *head)
{
	int N=lengthList(head);
	Node *p,*q;
	for (int i = 0; i < N - 1; i++)
	{
		p = head->next;
		q = p->next;
		for (int j = 0; j < N - i - 1; j++)
		{
			if (p->data > q->data)
			{
				p->pre->next = q;
				q->pre = p->pre;
				p->next = q->next;
				p->pre = q;
				q->next = p;
				p->next->pre = p;
				q = p->next;
				continue;
			}
			p = p->next;
			q = q->next;
		}
	}
}

当需要交换时:
在这里插入图片描述

8.销毁

直接head->pre->next=NULL;破坏链表结构,使其变为单向链表。

void destroyList(Node * head)
{
	head->pre->next=NULL;
	Node *tmp;
	while (head)
	{
		tmp = head;
		head = head->next;
		free(tmp);
	}
}

四、综合

#include<stdio.h>
#include<stdlib.h>
#include<time.h>
typedef struct node
{
	int data;
	struct node *pre;
	struct node *next;
}Node;

Node * createList();
void insertList(Node* head,int input);
void traverseNList(Node* head);
void traversePList(Node* head);
int lengthList(Node* head);
Node * findDataList(Node* head,int findData);
void deleteDataList(Node *pfind);
void sortList(Node *head);
void destroyList(Node * head);

int main()
{
	srand(time(NULL));
	Node * head = createList();
	for (int i = 0; i < 10; i++)
	{
		insertList(head,rand()%100);
	}
	printf("create and insert the list:\n");
	traverseNList(head);
	//traversePList(head);
	int listLen = lengthList(head);
	printf("\nlength of the list:%d\n",listLen);
	Node *flist = findDataList(head,0);
	if (flist)
	{
		printf("find!delete data 0\n");
		deleteDataList(flist);
		traverseNList(head);
	}
	else
		printf("find none!\n");
	printf("\nsort the list:\n");
	sortList(head);
	traverseNList(head);
	destroyList(head);
	
	return 0;
}
Node * createList()
{
	Node * head = (Node *)malloc(sizeof(Node));
	if (NULL == head)
		exit(-1);
	head->pre = head;
	head->next = head;
	return head;
}
void insertList(Node* head,int input)
{
	Node * ptr = (Node *)malloc(sizeof(Node));
	if (NULL == ptr)
		exit(-1);
	ptr->data = input;
	ptr->next = head->next;
	ptr->pre = head;
	head->next = ptr;
	ptr->next->pre = ptr;
}
void traverseNList(Node* head)
{
	Node* tmp = head->next;
	while (tmp != head)
	{
		printf("%-3d", tmp->data);
		tmp = tmp->next;
	}
}
void traversePList(Node* head)
{
	Node* tmp = head->pre;
	while (tmp != head)
	{
		printf("%-3d", tmp->data);
		tmp = tmp->pre;
	}
}
int lengthList(Node* head)
{
	int len = 0;
	Node* tmp = head->next;
	while (tmp != head)
	{
		len++;
		tmp = tmp->next;
	}
	return len;
}
Node * findDataList(Node* head, int findData)
{
	Node* fnext=head->next, *fpre = head->pre;
	while (fpre != fnext->pre)
	{
		if (findData == fnext->data)
			return fnext;
		if (findData == fpre->data)
			return fpre;
		if (fnext == fpre)
			break;
		fnext = fnext->next;
		fpre = fpre->pre;
	}
	return NULL;
}
void deleteDataList(Node *pfind)
{
	pfind->pre->next = pfind->next;
	pfind->next->pre = pfind->pre;
	free(pfind);
}
void sortList(Node *head)
{
	int N=lengthList(head);
	Node *p,*q;
	for (int i = 0; i < N - 1; i++)
	{
		p = head->next;
		q = p->next;
		for (int j = 0; j < N - i - 1; j++)
		{
			if (p->data > q->data)
			{
				p->pre->next = q;
				q->pre = p->pre;
				p->next = q->next;
				p->pre = q;
				q->next = p;
				p->next->pre = p;
				q = p->next;
				continue;
			}
			p = p->next;
			q = q->next;
		}
	}
}
void destroyList(Node * head)
{
	head->pre->next=NULL;
	Node *tmp;
	while (head)
	{
		tmp = head;
		head = head->next;
		free(tmp);
	}
}

在这里插入图片描述

猜你喜欢

转载自blog.csdn.net/Bryan_QAQ/article/details/95167761
今日推荐