双向单链表

//函数声明:#include"twowaylinklist.h"

#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#include<stdlib.h>
typedef int ElemType;
typedef struct DulNode
{
	struct DulNode *prior;
	ElemType data;
	struct DulNode *next;
}DulNode;

void judgement_NULL(DulNode *point);                //判断动态内存是否开辟成功
DulNode * creat();

void insert(DulNode *head, ElemType x, int i);       //在第i个位置上插入一个值为x的结点

void delete_element(DulNode *head, ElemType x);       //删除链表中所有的值为x的结点
void delete_place(DulNode *head, int i);               //删除第i个结点

void find_element(DulNode *head, int i);                  //寻找第i个结点上的元素
void find_place(DulNode *head, ElemType x);               //寻找所有值为x的结点

void length(DulNode *head);

void output_order(DulNode *head);                       //正向打印链表
void output_back(DulNode *head);                       //逆序打印链表

void initslinklist(DulNode *head);                     //释放整个链表

void sortrank(DulNode *head);                          //对链表进行排序

int means();                                     //选择以那种方式进行





#include"twowaylinklist.h"

void judgement_NULL(DulNode *point)              //判断开辟动态内存是否成功
{
	if (point == NULL)
	{
		perror("out of memory\n");
		exit(EXIT_FAILURE);
	}
}

DulNode * creat()                        //建立链表,以0作为结束标志
{
	printf("开始创建:");
	ElemType x;
	DulNode *head, *r, *p;
	head = (DulNode *)malloc(sizeof(DulNode));                 //开辟一个头结点
	judgement_NULL(head);
	head->prior = NULL;
	r = head;
	while (1)
	{
		scanf("%d", &x);
		if (x != 0)
		{
			p = (DulNode *)malloc(sizeof(DulNode));
			p->data = x;
			r->next = p;
			p->prior = r;
			r = p;
		}
		else
			break;
	}
	r->next = NULL;
	printf("创建成功\n");
	return head;                                               //返回头结点的地址
}
void insert(DulNode *head, ElemType x, int i)       //在第i个位置上插入一个结点,并且结点的data为x
{
	DulNode *p, *r;
	p = (DulNode *)malloc(sizeof(DulNode));                //建立这个结点 
	judgement_NULL(p);
	p->data = x;
	if (i == 1)                                               //考虑第一个结点的情况
	{
		p->next = head->next;
		head->next->prior = p;
		head->next = p;
		p->prior = head;
		printf("插入成功\n");
	}
	else
	{
		r = head->next;
		while (r != NULL)                       //找到这个结点
		{
			if (i == 1)
				break;
			r = r->next;
			i--;
		}
		if (r == NULL)
			printf("没有这个结点\n");
		else                                                        //如果这个结点存在
		{
			r->prior->next = p;
			p->prior = r->prior;
			p->next = r;
			r->prior = p;
			printf("插入成功\n");
		}
	}
}
void delete_element(DulNode *head, ElemType x)    //删除链表中所有的X元素
{
	DulNode *p, *r;
	int flag = 0;
	if (head->next == NULL)                         //考虑链表为空的情况
		printf("链表下溢\n");
	else
	{
		p = head->next;
		while (p != NULL)
		{
			if (p->data == x)
			{
				flag++;
				r = p;
				p = p->next;
				r->prior->next = r->next;
				r->next->prior = r->prior;
				free(r);
				r = NULL;
			}
			else
				p = p->next;
		}
		if (flag == 0)
			printf("没找到该元素\n");
		else
			printf("共删除%d个\n", flag);
	}
}
void delete_place(DulNode *head, int i)      //删除指定位置的结点
{
	DulNode *p;
	if (head->next == NULL)
		printf("链表下溢\n");
	else
	{
		p = head->next;
		while (p != NULL)                            //先找到这个位置
		{
			if (i == 1)
				break;
			p = p->next;
			i--;
		}
		if (p == NULL)
			printf("没有此位置\n");
		else
		{
			p->prior->next = p->next;
			p->next->prior = p->prior;
			free(p);
			p = NULL;
			printf("删除成功\n");
		}
	}
}
void find_element(DulNode *head, int i)               //查找第i个结点上的data,找到并输出
{
	DulNode *p;
	if (head->next == NULL)
		printf("链表下溢\n");
	else
	{
		p = head->next;
		while (p != NULL)
		{
			if (i == 1)
				break;
			p = p->next;
			i--;
		}
		if (p == NULL)
			printf("没有该结点\n");
		else
			printf("结点元素:%d\n", p->data);
	}
}
void find_place(DulNode *head, ElemType x)       //找到链表中所有data为x的结点,并输出结点位置
{
	DulNode *p;
	int i = 0;
	int flag = 0;
	if (head->next == NULL)
		printf("链表下溢\n");
	else
	{
		p = head->next;
		while (p != NULL)
		{
			i++;
			if (p->data == x)
			{
				flag++;
				printf("此元素的结点位置:%d\n",i);
			}
			p = p->next;
		}
		if (flag == 0)
			printf("链表中没有该结点\n");
	}
}
void length(DulNode *head)              //求链表长度
{
	DulNode *p = head->next;
	int len = 0;
	if (head->next == NULL)
		printf("链表长度为:%d\n", len);
	else
	{
		while (p != NULL)               
		{
			len++;
			p = p->next;
		}
		printf("链表长度:%d\n", len);
	}
}
void output_order(DulNode *head)        //正向打印链表
{
	DulNode *p = head->next;
	if (head->next == NULL)
		printf("链表为空");
	else
	{
		printf("顺序打印链表:");
		while (p != NULL)
		{
			printf("%d ", p->data);
			p = p->next;
		}
	}
	printf("\n");
}
void output_back(DulNode *head)         //反向打印链表
{
	DulNode *p;
	if (head->next == NULL)
		printf("链表为空");
	else
	{
		printf("逆序打印链表:");
		p = head->next;
		while (p->next != NULL)                  //让p指向最后一个结点
		{
			p = p->next;
		}
		while (p != head)
		{
			printf("%d ", p->data);
			p = p->prior;
		}
	}
	printf("\n");
}
void initslinklist(DulNode *head)                         //释放当前链表
{
	DulNode *p,*r;
	p = head;
	while (p != NULL)
	{
		r = p;
		p = p->next;
		free(r);
		r= NULL;
	}
	head = NULL;
	printf("初始化成功\n");
}

void sortrank(DulNode *head)
{
	DulNode *p, *r;
	p = head->next;
	ElemType tmp;
	while (p != NULL)                //使用冒泡排序
	{
		r = head->next;
		while (r->next != NULL)
		{
			if ((r->data) > (r->next->data))
			{
				tmp = r->data;
				r->data = r->next->data;
				r->next->data = tmp;
			}
			r = r->next;
		}
		p = p->next;
	}
	printf("排序成功\n");
}

int means()
{
	int m = 0;
	while (1)
	{
		printf("请选择方式:");
		scanf("%d", &m);
		if (m == 1 || m == 2)
			break;
		printf("选择无效,请重新选择\n");
	}
	return m;
}







//函数测试:"twowaylinklist.c"

#include"twowaylinklist.h"

int main()
{
	DulNode *ret = NULL;
	int n = 0;
	int i = 0;
	ElemType x;
	printf("*********************************************\n");
	printf("*********************************************\n");
	printf("*1.CreatLinkList      2.Insert  *********\n");
	printf("*3.Delete        4.Find   *********\n");
	printf("*5.Length        6.Output  *********\n");
	printf("*7.InitsLinkLinst    8.Sortrank  ********\n");
	printf("*0.Exit          *********************\n\n\n");

	while (1)
	{
		printf("请选择功能:");
		scanf("%d", &n);
		if (n == 0)                       //选择0直接退出
		{
			free(ret);                     //退出前先释放列表
			exit(1);
		}
		if (ret == NULL)                     //如果ret为空,则首先建立链表
		{
			if (n == 1)
			{
				printf("创建链表以0作为结束标志\n");
				ret = creat();
			}
			else
				printf("请先建立链表\n");
		}		
		else
		{
			switch (n)                       //选择剩下的功能
			{
			case 1:                        //当ret为空时才能建立链表
				printf("当前链表未结束,请先初始化链表\n");
				break;
			case 2:
				printf("请输入要插入的元素和位置:");
				scanf("%d", &x);
				scanf("%d", &i);
				insert(ret, x, i);
				break;
			case 3:
				printf("*1.delete_element     2.delete_place*\n");
				if (means() == 1)
				{
					printf("请输入要删除的元素:");
					scanf("%d", &x);
					delete_element(ret, x);
				}
				else
				{
					printf("请输入要删除的结点:");
					scanf("%d", &i);
					delete_place(ret, i);
				}
				break;
			case 4:
				printf("*1.find_place         2.find_element*\n");
				if (means() == 1)
				{
					printf("请输入要查找的元素:");
					scanf("%d", &x);
					find_place(ret, x);
				}
				else
				{
					printf("请输入要查找的位置:");
					scanf("%d", &i);
					find_element(ret, i);
				}
				break;
			case 5:
				length(ret);
				break;
			case 6:
				printf("*1.output_order         2.output_back*\n");
				if (means() == 1)
					output_order(ret);
				else
					output_back(ret);
				break;
			case 7:                     //将当前链表释放
				initslinklist(ret);
				ret = NULL;
				break;
			case 8:
				sortrank(ret);
				break;
			default:
				printf("选择无效,请重新选择\n");
				break;
			}
		}
		n = 0;
	}
	system("pause");
	return 0;
}

j_0035.gif

你可能感兴趣的:(双向单链表)