一、循环链表
1、尾指针的后继就是头节点,每一个指针都含有前驱指针和后继指针。
2、查找终端节点和尾节点的时间复杂度是O(1)。
3、易错点
1、带头节点的双链表L为空表是应满足:L->next=NULL;
2、带有头节点的循环单链表L,成为空表时有表头节点的指针域next和L的值相等
3、长度为n的循环单链表L,删除尾节点的时间复杂度是o(n)
4、相关算法
/*合并两个循环链表A和B*/
p=rearA->next;//p是表A的开始节点
rearA->next=reaB->next->next;//将表B的第一个节点(不是头节点)赋值给A的开始节点
rearB->next=p;//把B和A连上
q=rearB->next;//原来B的头节点
free(q);//多出来的头节点释放掉
二、双向链表
1、双向链表的节点有两个指针域,一个指向前驱元素,一个指向后继元素。
2、双向链表的大部分操作与单链表相同,例如求ListLength,GetElem,LocateElem只需要涉及一个指针就可以了。
3、相关算法
typedef struct DoubleNode
{
int data;
Node prior;
Node next;
}DoubleList;
typedef struct DoubleNode *Node
typedef struct
{
int size;
Node head;//头
Node rear;//尾
}list;
/*插入元素*/
/*操作:在p节点之后插入新节点s*/
int InsertNode(DoubleList *L,Node p,Node s)
{
s->prior=p;
s->next=p->next;
p->next->prior=s;
p->next=s;
L->size++;
/*删除元素*/
/*操作:删除节点P*/
int DelNode(DoubleList *L,Node p)
{
p->prior->next=p->next;
p->next->prior=p->prior;
free(p);
L->size--;
}