为了引出Linux中使用的循环链表,大家熟悉下一般的循环链表的情况,可能比较简单
一般双向循环链表的实现
例子所用的结构体如下:
- #include <stdio.h>
- #include <stdlib.h>
-
- typedef int data_type;
-
- typedef struct double_listnode {
- data_type data;
- struct double_listnode *prior, *next;
- }double_listnode_t, *double_listnode_p;
双向循环链表的运算
(1)、创建(带头结点)
通过循环依次创建n个数据域为整数的结点,示例代码如下:
- static double_listnode_t *init_double_list(int n)
- {
- int i;
- double_listnode_p head, p, s;
-
- head = (double_listnode_t *)malloc(sizeof(double_listnode_t));
- head -> prior = head -> next = head;
-
- p = head;
- for (i = 0; i < n; i++) {
- s = (double_listnode_t *)malloc(sizeof(double_listnode_t));
- s -> data = i + 1;
-
- s -> next = head;
- head -> prior = s;
-
- s -> prior = p;
- p -> next = s;
-
- p = s;
- }
-
- return head;
- }
(2)、按结点在链表中的位置查找
示例代码如下:
- static double_listnode_t *get_double_listnode(double_listnode_p head, int i)
- {
- double_listnode_p p = head;
- int j = 0;
-
- while (p -> next != head && j < i) {
- p = p -> next;
- j++;
- }
-
- if (i == j)
- return p;
- else
- return NULL;
- }
(3)、在链表中的i位置插入一个结点
首先要获得i-1结点的地址,然后初始化数据域并插入,示例代码如下:
- static void insert_double_listnode(double_listnode_p head, int i, data_type data)
- {
- double_listnode_p tmp, p = NULL;
-
- p = get_double_listnode(head, i - 1);
- if (p == NULL) {
- fprintf(stderr, "position error\n");
- exit(-1);
- }
-
- tmp = (double_listnode_t *)malloc(sizeof(double_listnode_t));
- tmp -> data = data;
-
- tmp -> prior = p;
- tmp -> next = p -> next;
-
- p -> next -> prior = tmp;
- p -> next = tmp;
- }
(4)、删除链表的i结点
先获得i结点的地址,然后删除,示例代码如下:
- static void delete_double_listnode(double_listnode_p head, int i)
- {
- double_listnode_p p = NULL;
-
- p = get_double_listnode(head, i);
- if (p == NULL || p == head) {
- fprintf(stderr, "position error\n");
- exit(-1);
- }
-
- p -> prior -> next = p -> next;
- p -> next -> prior = p -> prior;
-
- free(p);
- }
(5)、打印链表
示例代码如下:
- static void print_double_listnode(double_listnode_p head)
- {
- double_listnode_p p = head -> next;
-
- while (p != head) {
- printf("%d ", p -> data);
- p = p -> next;
- }
- printf("\n");
- }
(6)、销毁链表
示例代码如下:
- static void destroy_double_list(double_listnode_p head)
- {
- double_listnode_p s, p = head -> next;
-
- while (p != head) {
- s = p;
- p = p -> next;
- free(s);
- }
- free(head);
- }
综合测试上述所讲函数的代码如下:
- int main(void)
- {
- int a = 10;
- double_listnode_p head;
-
- head = init_double_list(a);
- print_double_listnode(head);
-
- insert_double_listnode(head, 7, 11);
- print_double_listnode(head);
-
- delete_double_listnode(head, 5);
- print_double_listnode(head);
-
- destroy_double_list(head);
-
- return 0;
- }