一.循环单链表:
- 定义循环单链表
和普通单链表一样:
typedef struct LNode{
ElemType data;
struct LNode *next;
}LNode,*LinkList;
- 初始化循环单链表:
bool InitList(LinkList &L){
L=(LNode*)malloc(sizeof(LNode)); //分配一个单链表
if(L==NULL);
return false;
L->next=L; //头结点指向自己
return true;
}
- 判断循环单链表是否为空:
bool Empty(LinkList L){
return (L->next==L);
}
- 判断指定结点是否为尾结点:
bool IsTail(LinkList L,LNode *p){
return (p->next==L);
}
二.循环双链表:
- 循环双链表的定义:
typedef struct DNode{
Elemtype data;
struct DNode *next,*prior;
}DNode,*DLinkList;
- 循环双链表的初始化:
bool InitDLinkList(DLinkList &L){
L=(DNode*)malloc(sizeof(DNode));
if(L==NULL)
return false;
L->next=L;
L->prior=L;
return true;
}
- 判断循环双链表是否为空:(与单链表相同)
bool Empty(DLinkList L){
return (L->next==L); //&&L->prior==L可以省略
}
- 指定结点是否为尾结点:(与单链表相同 )
bool IsTail(DNode *p,DLinkList L){
return (p->next==L);
}
- 循环双链表的插入:
之前双链表的插入虽然也是如此,但是在最后一个结点插入时会出现问题。因为p->next->prior会返回空指针错误。
//p结点后插入s结点
bool InsertNextDNode(DNode *p,DNode *s){
s->prior=p;
s->next=p->next;
p->next->prior=s;
p->next=s;
return true;
}
- 循环双链表的删除:
//在p结点后删除s
bool DeletDNode(DNode *p,DNode *s){
p->next=s->next;
s->next->prior=p;
free(s);
return true;
}
以上许多操作少写了异常判断,应该加入判断传入指针是否为空指针的语句。(作业太多了,偷懒ing。。。)
总结一下,循环链表主要是可以方便操作头结点尾结点(尤其尾结点)
,尾结点的下一个结点是头结点。