目录
1、循环单链表
循环单链表和单链表的区别在于,表中最后一个结点的柱子很不是NULL,而改为指向头结点,从而整个链表形成一个环。如图11.1所示。
图11.1 循环单链表
在循环单链表中,表尾结点*r的next域指向L,故表中没有指针域为NULL的结点,因此,循环单链表的判空条件不是头结点的指针是否为空,而是它是否等于头指针(也就是说是否自己指向自己)
循环单链表的插入、删除算法和单链表的几乎一样,所不同的是若操作是在表尾进行,则执行的操作不同,以让单链表继续保持循环的特性。当然,正是因为循环单链表是一个“环”,因此在任何一个位置上的插入和删除操作都是无价的,无需判断是否表尾。
在单链表中只能从表头结点开始往后顺序遍历整个链表,而循环单链表可以从表中的任意一结点开始遍历整个链表。又是对单链表常做的操作是在表头和表尾进行的,此时对循环单链表不设头指针而仅设尾指针,从而使得操作效率更高。其原因是,若设的是头指针,对表尾进行操作需要O(n)的时间复杂度,而若是设的尾指针r,r->next即为头指针,对于表头表尾都只需要O(1)的时间复杂度。
2、循环双链表
由循环双链表的定义不难推出循环双链表,不同的是在循环双链表中,头结点的prior指针还要指向表尾结点,如图11.2所示
图11.2 循环双链表
在循环双链表L中,某结点*p为尾结点时,p->next == L。当循环双链表为空时,其头结点的prior域和next域都指向L。
3、静态链表
静态链表借助数组来描述线性表的链式存储结构,结点也有数据域data和指针域next,与前面所讲的链表中的指针不同的是,这里的指针是结点的相对地址(数组下标),又称游标。和顺序表一样,静态链表也要预先分配一块连续的内存空间。
图11.3 静态链表存储示意图
上图(a)的第一列是data域,第二列是next域
静态链表结构描述如下:
#define MaxSize 50
typdef struct
{
ElemType data;
int next;
}SLinkList[MaxSize];
静态链表以-1代替一般链表中next域中的NULL值,这样的结构有局限性,但是也有好处,特别是在一些不支持指针的语言中可以这样使用,而且效率高,操作的时间复杂度O(1)
人,总是要有一点精神的,不是吗