1.lianbiao.h
#include<stdio.h>
#include<stdlib.h>
#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0
#define INFEASIBLE -1
#define OVERFLOW -2
#define LIST_LEN 100
typedef int Status;
typedef int ElemType;
typedef struct LNode{//结点类型
ElemType data;
struct LNode *next;
}*Link,*Position;
typedef struct{//链表类型
Link head,tail;//分别指向线性链表中的头结点和最后一个结点
int len; //指示线性链表中数据元素的个数
}LinkList;
Status MakeNode(Link &p,ElemType e);
//分配由p指向e的结点,并返回OK;若分配失败,则返回ERROR
void FreeNode(Link &p);
//释放P所指结点
Status InitList(LinkList &L);
//1构造一个空的线性链表
Status DestroyList(LinkList &L);
//2销毁线性链表L,L不再存在
Status ClearList(LinkList &L);
//3 将线性链表L重置为空表,并释放原链表的结点空间
Status InsFirst(Link h,Link s);
//4 已知h指向线性链表的头结点,将s所指结点插入在第一个结点之前
Status DelFirst(Link h,Link &q);
//5 已知h指向线性链表的头结点,删除链表中的第一个结点并以q返回
Status Append(LinkList &L,Link s);
//6 将指针s所指的一串结点链接在线性链表L的最后一个结点
//之后,并改变链表L的尾指针指向新的尾结点
Status Remove(LinkList &L,Link &q);
//7 删除线性链表L中的尾结点并以q返回,改变链表L的尾指针指向新的尾结点
Status InsBefore(LinkList &L,Link &p,Link s);
//8 已知p指向线性链表L中的一个结点,将s所指结点插入在p所指结点之前,
//并修改指针p指向新插入的结点
Status InsAfter(LinkList &L, Link &p, Link s);
//9 已知p指向线性链表L中的一个结点,将s所指结点插入在p所指结点之后,
//并修改指针p指向新插入的结点
Status SetCurElem(Link &p,ElemType e);
//10 已知p指向线性链表中的一个结点,用e更新p所指结点中数据元素的值
ElemType GetCurElem(Link p);
//11 已知p指向线性链表中的一个结点,返回p所指结点中数据元素的值
Status ListEmpty(LinkList L);
//12 若线性链表L为空表,则返回TRUE,否则返回FALSE
int ListLength(LinkList L);
//13 返回线性链表L中元素个数
Position GetHead(LinkList L);
//14 返回线性链表L中头结点的位置
Position GetLast(LinkList L);
//15 返回线性链表L中最后一个结点的位置
Position PriorPos(LinkList L, Link p);
//16 已知p指向线性链表L中的一个结点,返回p所指结点的直接前驱的位置
//若无前驱,则返回NULL
Position NextPos(LinkList L, Link p);
//17 已知p指向线性链表L中的一个结点,返回p所指结点的直接后继的位置
//若无后继,则返回NULL
Status LocatePos(LinkList L,int i,Link &p);
//18 返回p指示线性链表L中第i个结点的位置并返回OK,i值不合法时返回ERROR
Status compare(ElemType a,ElemType b);
Position LocateElem(LinkList L,ElemType e,Status (*compare)(ElemType,ElemType));
//19 返回线性链表L中第1个与e满足compare()判定关系的元素的位置
//若不存在这样的元素,则返回NULL
Status visit(ElemType x);
Status ListTraverse(LinkList L,Status(*visit)(ElemType));
//20 依次对L的每个元素调用函数visit(),一旦visit()失败,则操作失败。
2.lianbiao.cpp
#include "lianbiao.h"
Status MakeNode(Link &p,ElemType e)
{
p = (LNode*)malloc(1 * sizeof(LNode));
p->data=e;
if(p) return OK;
else return ERROR;
}
void FreeNode(Link &p)
{
free(p);
p=NULL;
}
Status InitList(LinkList &L)
{
L.head=(LNode*)malloc(1 * sizeof(LNode));
L.head->next=NULL;
L.tail=L.head;
L.len=0;
if(L.head) return OK;
else return ERROR;
}
Status DestroyList(LinkList &L)
{
ClearList(L);
free(L.head);
L.head = NULL;
L.tail = NULL;
if(!L.head) return OK;
else return ERROR;
}
Status ClearList(LinkList &L)
{
Link p = L.head->next;
while(p){
L.head->next = p->next;
free(p);
p = NULL;
L.len--;
p = L.head->next;
}
if(L.head->next==NULL) return OK;
else return ERROR;
}
Status InsFirst(Link h,Link s)
{
s->next = h->next;
h->next = s;
return OK;
}
Status DelFirst(Link h,Link &q)
{
q = h->next;
Link p=h->next;
if(p){
h->next = p->next;
return OK;
}else
return ERROR;
}
Status Append(LinkList &L,Link s)
{
L.tail->next = s;
while((L.tail->next)!=NULL){
L.len++;
L.tail = L.tail->next;
}
return OK;
}
Status Remove(LinkList &L,Link &q)
{
if(!L.head){
printf("线性链表不存在");
return ERROR;
}
q = L.head;
while(q->next!=L.tail){
q = q->next;
}
L.tail = q;
q = q->next;
L.tail->next = NULL;
L.len--;
return OK;
}
Status InsBefore(LinkList &L, Link &p, Link s)
{
Link q = L.head;
if(!L.head){
printf("线性链表不存在");
return ERROR;
}
while(q->next!=p){
q = q->next;
}
q->next = s;
s->next = p;
p = s;
L.len++;
return OK;
}
Status InsAfter(LinkList &L, Link &p, Link s)
{
if(!L.head){
printf("线性链表不存在");
return ERROR;
}
s->next = p->next;
p->next = s;
if(p==L.tail)
L.tail = L.tail->next;
p = s;
L.len++;
return OK;
}
Status SetCurElem(Link &p,ElemType e)
{
p->data=e;
return OK;
}
ElemType GetCurElem(Link p)
{
return p->data;
}
Status ListEmpty(LinkList L)
{
if(!L.head){
printf("线性链表不存在");
return ERROR;
}
if(L.head->next==NULL)
return OK;
else
return ERROR;
}
int ListLength(LinkList L)
{
if(!L.head){
printf("线性链表不存在");
return ERROR;
}
return L.len;
}
Position GetHead(LinkList L)
{
if(!L.head){
printf("线性链表不存在");
return ERROR;
}
return L.head;
}
Position GetLast(LinkList L)
{
if(!L.head){
printf("线性链表不存在");
return ERROR;
}
return L.tail;
}
Position PriorPos(LinkList L, Link p)
{
Link q = L.head;
if(!L.head){
printf("线性链表不存在");
return ERROR;
}
if(p==L.head)
return NULL;
while(q->next!=p){
q = q->next;
}
return q;
}
Position NextPos(LinkList L, Link p)
{
if(!L.head){
printf("线性链表不存在");
return ERROR;
}
if(p==L.tail)
return NULL;
return p->next;
}
Status LocatePos(LinkList L,int i,Link &p)
{
int j = 0;
Link pt = L.head;
while(pt&&j<i)
{
pt = pt->next;
j++;
}
if(!pt||j>i)
return ERROR;
else{
p=pt;
return OK;
}
}
Status compare(ElemType a,ElemType b)
{
if(a==b)
return OK;
else
return ERROR;
}
Position LocateElem(LinkList L,ElemType e,Status (*compare)(ElemType,ElemType))
{
Link q = L.head->next;
while(q->next!=NULL)
{
if(compare(q->data,e))
return q;
q = q->next;
}
return NULL;
}
Status visit(ElemType x)
{
printf("%d ",x);
return OK;
}
Status ListTraverse(LinkList L,Status(*visit)(ElemType))
{
Link q = L.head->next;
printf("遍历线性链表结果如下:\n");
while(q)
{
if(visit(q->data))
q = q->next;
else
return ERROR;
}
printf("\n");
return OK;
}
3.main.cpp
#include "lianbiao.h"
int main()
{
Link p,he,s;
ElemType e;
LinkList L;
printf("%d 如果为1则构造空线性链表成功,否则不成功\n",InitList(L));
he=L.head;
printf("请输入要插入的第一个结点数据:");
scanf("%d",&e);
MakeNode(p,e);
printf("%d 如果为1则表示在第一个结点前插入元素成功,否则不成功\n",InsFirst(he,p));
printf("%d 如果为1则表示第一个结点已经删除,否则删除不成功\n",DelFirst(he,p));
printf("删除的第一个结点元素数据为%d\n",p->data);
int n;
printf("请输入要构建几个元素的链表:");
scanf("%d",&n);
printf("请输入这几个元素数据:");
for(int i=1;i<=n;i++)
{
scanf("%d",&e);
MakeNode(p,e);
p->next=NULL;
printf("%d 如果为1表示在尾结点插入成功且链表元素个数更新,否则不成功\n",Append(L,p));
}
printf("插入后元素个数为%d\n",L.len);
e=6;
MakeNode(s,e);
printf("%d 如果为1表示插入在所指结点前成功,否则不成功\n",InsBefore(L,p,s));
printf("p所指结点数据为%d\n",p->data);
e=7;
MakeNode(s,e);
printf("%d 如果为1表示插入在所指结点后成功,否则不成功\n",InsBefore(L,p,s));
printf("p所指结点数据为%d\n",p->data);
e=7;
printf("%d 如果为1表示用e更新p所指结点数据成功,否则不成功\n",SetCurElem(p,e));
printf("p所指结点数据的值为%d\n",p->data);
printf("p所指结点数据值为%d\n",GetCurElem(p));
printf("线性链表长度为%d\n",ListLength(L));
printf("线性链表头结点位置%p\n",GetHead(L));
printf("线性链表尾结点位置%p\n",GetLast(L));
printf("p所指结点前驱位置%p\n",PriorPos(L,p));
p=L.head->next;
printf("p所指结点后继位置%p\n",NextPos(L,p));
printf("请选择要查找的结点:");
scanf("%d",&n);
printf("%d 如果为1表示该结点查找成功,否则不成功\n",LocatePos(L,n,p));
printf("p所指结点后继位置%p\n",p);
n=4;
printf("符合相等值的元素位置为%p\n",LocateElem(L,n,(*compare)));
printf("%d 如果为1表示遍历线性链表成功,否则不成功\n",ListTraverse(L,(*visit)));
printf("%d 如果为1表示线性链表置空成功,否则不成功\n",ClearList(L));
printf("%d 如果为1表示线性链表是空表,否则不是空表\n",ListEmpty(L));
printf("%d 如果为1表示线性链表已经销毁,否则没有销毁\n",DestroyList(L));
return 0;
}
运行截图