/*
作用:双链表及其各种方法的实现(C语言)
日期:2015年5月
作用:双链表及其各种方法的实现(C语言)
日期:2015年5月
*/
//DList.h
//结构体定义及函数声明
#ifndef DLIST_H
#define DLIST_H
#include<iostream>
#include<assert.h>
using namespace std;
#define ElemType int
typedef struct Node
{
ElemType data;
struct Node *prio;
struct Node *next;
}Node,*PNode;
typedef struct List
{
PNode head;
PNode tail;
int size;
}List,*PList;
void InitList(PList list); //初始链表
void push_back(PList list,ElemType x); //尾插
void push_front(PList list,ElemType x); //头插
void show_DList(PList list); //显示链表
void pop_back(PList list); //删除最后面一个节点
void pop_front(PList list); //删除最前面一个节点
void insert_val(PList list,ElemType x); //链表有序的前提下,插入一个节点到适当位置
PNode find(PList list,ElemType key); //给一个值,看这个节点是否找到或存在
void delete_val(PList list,ElemType key); //删除给定的值
void modify(PList list,ElemType key1,ElemType key2); //把原有的key1修改成key2
void clear(PList list); //清空链表
void destroy(PList list); //摧毁链表
void sort(PList list); //把无序的链表排成有序
void reserve(PList list); //把链表转置
int length(PList list); //求链表的长度
ElemType next(PList list,ElemType x); // 求给定值的后继值
ElemType prio(PList list,ElemType x); // 求给定值的前驱值
#endif
//DList.cpp
//各种函数的实现方法
#include"DList.h"
void InitList(PList list)
{
Node *s = (Node *)malloc(sizeof(Node));
assert(s != NULL);
s->prio = NULL;
s->next = NULL;
list->head = list->tail = s;
list->size = 0;
}
void push_back(PList list,ElemType x)
{
PNode s = (PNode)malloc(sizeof(Node));
assert(NULL != s);
s->data = x;
s->next = NULL;
list->tail->next = s;
s->prio = list->tail;
list->tail = s;
list->size++;
}
void push_front(PList list,ElemType x)
{
PNode s = (PNode)malloc(sizeof(Node));
s->data = x;
if(0 != list->size)
{
s->next = list->head->next;
list->head->next->prio = s;
}
else
{
s->next = NULL;
list->tail = s;
}
list->head->next = s;
s->prio = list->head;
list->size++;
}
void show_DList(PList list)
{
if(0 == list->size)
{
cout<<"--链表为空"<<endl;
return ;
}
PNode p = list->head->next;
while(NULL != p)
{
cout<<p->data<<" ";
p = p->next;
}
cout<<endl;
}
void pop_back(PList list)
{
if(0==list->size)
{
cout<<"--链表为空,不能删除"<<endl;
return ;
}
PNode p = list->tail;
if(1 == list->size)
{
free(list->tail);
list->tail = list->head;
list->head->next = NULL;
}
else
{
list->tail = list->tail->prio;
list->tail->next = NULL;
free(p);
}
list->size--;
}
void pop_front(PList list)
{
if(0==list->size)
{
cout<<"--链表为空,不能删除"<<endl;
return ;
}
PNode p = list->head->next;
if(1==list->size)
{
free(list->tail);
list->tail = list->head;
list->head->next = NULL;
}
else
{
list->head->next = p->next;
p->next->prio = list->head;
free(p);
}
list->size--;
}
void insert_val(PList list,ElemType x)
{
PNode p = list->head->next;
while(NULL != p && p->data < x ) //循环结束后,新节点插入p的前面一个节点
{
p = p->next;
}
if(NULL == p)
{
push_back(list,x);
}
else
{
PNode s = (PNode)malloc(sizeof(Node));
s->data = x;
p->prio->next = s;
s->prio = p->prio;
s->next = p;
p->prio = s;
list->size++;
}
cout<<"--"<<x<<"已被插入到适当位置!"<<endl;
}
PNode find(PList list,ElemType key) //函数返回值为key的节点地址
{
if(0==list->size)
return NULL;
PNode p = list->head->next;
while(NULL != p && key != p->data)
{
p=p->next;
}
if(NULL == p)
cout<<"--没有找到 "<<key<<"!"<<endl;
return p;
}
void delete_val(PList list,ElemType key)
{
PNode p = find(list,key);
if(NULL == p)
return ;
if(p == list->head->next)
pop_front(list);
else
{
if(p==list->tail)
pop_back(list);
else
{
p->prio->next = p->next;
p->next->prio = p->prio;
free(p);
list->size--;
}
}
cout<<key<<"节点已被删除!"<<endl;
}
void modify(PList list,ElemType key1,ElemType key2)
{
PNode p = find(list,key1);
if(NULL != p)
{
p->data = key2;
cout<<key1<<" 已被修改成 "<<key2<<"."<<endl;
}
return ;
}
void clear(PList list)
{
PNode p = list->head->next;
PNode q = list->head;
while(NULL != p && NULL != p->next)
{
p = p->next;
q = p->prio;
free(q);
}
free(p);
list->head->next = NULL;
list->tail = list->head;
list->size = 0;
cout<<"--链表已被清空!"<<endl;
}
void destroy(PList list)
{
clear(list);
free(list->head);
list->head = NULL;
list->tail = NULL;
cout<<"--链表已被摧毁!"<<endl;
}
void sort(PList list) //插入排序
{
ElemType tmp = 0;
PNode p = list->head->next;
PNode q = NULL;
for(p = p->next;p != NULL;p = p->next)
{
if(p->data<p->prio->data)
{
tmp = p->data;
for(q = p->prio;q->data>tmp; q= q->prio)
{
q->next->data = q->data;
}
q->next->data = tmp;
}
}
cout<<"--链表已按从小到大排列!"<<endl;
}
void reserve(PList list)
{
if(0==list->size)
return ;
PNode s =(PNode)malloc(sizeof(Node));
PNode p = list->tail;
list->tail = s;
while(list->head != p)
{
list->tail->next = p;
p = p->prio;
p->next->prio = list->tail;
list->tail = list->tail->next;
}
list->tail->next = NULL;
free(list->head);
list->head = s;
cout<<"--链表已转置!"<<endl;
}
int length(PList list)
{
return list->size;
}
ElemType next(PList list,ElemType x)
{
PNode p = find(list,x);
if(list->tail == p)
{
cout<<x<<"没有后继"<<endl;
return -1;
}
return p->next->data;
}
ElemType prio(PList list,ElemType x)
{
PNode p = find(list,x);
if(list->head->next == p)
{
cout<<x<<"没有前驱"<<endl;
return -1;
}
return p->prio->data;
}
//main.cpp
//测试函数
#include "DList.h"
void main()
{
List mylist;
InitList(&mylist);
int select = 1;
ElemType item;
Node *p = NULL;
int pos;
while(select)
{
cout<<"*********************************************************************"<<endl;
cout<<"* [0] quit_system [1] push_back [2] push_front [3] show_DList *"<<endl;
cout<<"* [4] pop_back [5] pop_front [6] insert_val [7] delete_val *"<<endl;
cout<<"* [8] find [9] modify [10] clear [11] destroy *"<<endl;
cout<<"* [12] sort [13] resver [14] length [15] next *"<<endl;
cout<<"* [16] prio *"<<endl;
cout<<"*********************************************************************"<<endl;
cout<<"请选择:>";
cin>>select;
switch(select)
{
case 0:
destroy(&mylist);
select = 0;
break;
case 1:
cout<<"--请输入要尾插的数据(-1结束):>"<<endl;;
while(cin>>item,item!=-1)
{
push_back(&mylist,item);
}
break;
case 2:
cout<<"--请输入要头插的数据(-1结束):>"<<endl;;
while(cin>>item,item!=-1)
{
push_front(&mylist,item);
}
break;
case 3:
show_DList(&mylist);
break;
case 4:
pop_back(&mylist);
break;
case 5:
pop_front(&mylist);
break;
case 6:
cout<<"请输入要插入的值:";
cin>>item;
insert_val(&mylist,item);
break;
case 7:
cout<<"--请输入要删除的值"<<endl;
cin>>item;
delete_val(&mylist,item);
break;
case 8:
cout<<"--请输入要查找的值:";
cin>>item;
p = find(&mylist,item);
if(NULL != p)
cout<<"--"<<p->data<<"已找到."<<endl;
break;
case 9:
cout<<"--请输入要修改的的值和新值:";
cin>>pos>>item;
modify(&mylist,pos,item);
break;
case 10:
clear(&mylist);
break;
case 11:
destroy(&mylist);
break;
case 12:
sort(&mylist);
break;
case 13:
reserve(&mylist);
break;
case 14:
cout<<"链表长度为:"<<length(&mylist)<<endl;
break;
case 15:
cout<<"--请输入要找哪个值的后继:";
cin>>item;
cout<<item<<"的后继是:"<<next(&mylist,item)<<endl;
break;
case 16:
cout<<"--请输入要找哪个值的前驱:";
cin>>item;
cout<<item<<"的前驱是:"<<prio(&mylist,item)<<endl;
break;
default:
break;
}
}
}
//测试结果: