数据结构-链表顺序结构、链式结构(单链表、循环链表、双向链表)

本文详细介绍了线性表的顺序存储与链式存储结构,包括单链表、循环链表及双向链表的实现原理与操作方法,如初始化、插入、删除等,并通过实例演示了各方法的应用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

线性结构顺序存储结构

// 优点:
// 1.无须关系表中元素之间的关系。
// 2.可以快速的得到任何元素
// 缺点:
// 1.插入和删除需要移动大量的元素
// 2.当线性表过大时,无法确定元素的大小
// 3.容易造成内存碎片

#include "stdio.h"
#define MAXLEN 10
typedef struct LIST{
    int Data[MAXLEN];
    int len;
} List;

// 初始化
void init(List* list);
// 线性表是否为空
int isEmpty(List list);
// 插入元素
int insertData(List* list, int index, int number);
// 删除元素
int deleteData(List* list, int index);
// 线性表长度
int getLen(List list);
// 清空线性表元素
int clearList(List list);
// 获取线性表元素
int getListData(List list, int index);
// 显示线性表所有元素
int showList(List list);

int main()
{
    int ret;
    List a;
    init(&a);
    ret = showList(a);
    if (ret != 0) {
        printf("show list error\n");
        return -11;
    }
    ret = insertData(&a, 0, 10);
    if (ret != 0) {
        printf("insertData list error\n");
        return -11;
    }
    ret = insertData(&a, 1, 20);
    if (ret != 0) {
        printf("insertData list error\n");
        return -11;
    }
    ret = insertData(&a, 2, 30);
    if (ret != 0) {
        printf("insertData list error\n");
        return -11;
    }
    ret = insertData(&a, 3, 40);
    if (ret != 0) {
        printf("insertData list error\n");
        return -11;
    }
    ret = showList(a);
    if (ret != 0) {
        printf("showList list error\n");
        return -11;
    }
    printf("list a len = %d\n",getLen(a));
    ret = deleteData(&a, 4);
    if (ret != 0) {
        printf("deleteData list error\n");
        return -11;
    }
    printf("list a len = %d\n",getLen(a));
    ret = showList(a);
    if (ret != 0) {
        printf("showList list error\n");
        return -11;
    }
    printf("get list data = %d\n",getListData(a,3));
    ret = clearList(a);
    if (ret != 0) {
        printf("clearList list error\n");
        return -11;
    }
    ret = showList(a);
    if (ret != 0) {
        printf("showList list error\n");
        return -11;
    }

    return 0;
}


void init(List* list)
{
    list->len = 0;
}
int isEmpty(List list)
{
    if (list.len == 0) {
        return 0;
    }
    return -1;
}
int insertData(List* list, int index, int number)
{
    if (list == NULL) {
        printf("addData fucntion param(list) error...return -1\n");
        return -1;
    }

    if (index > MAXLEN) {
        printf("addData fucntion param(i) error...return -1\n");
        return -1;
    }

    if (index == 0 && list->len == 0) {
        list->Data[0] = number;
        list->len++;
        return 0;
    }else if(index == list->len)
    {
        list->Data[list->len] = number;
        list->len++;
        return 0;
    }

    for(int i = list->len; i >= index-1; i--){
        list->Data[i] = list->Data[i-1];
    }
    list->Data[index-1] = number;
    list->len++;

    return 0;
}

int deleteData(List* list, int index)
{
    if (list == NULL) {
        printf("deleteData fucntion param(list) error...return -1\n");
        return -1;
    }
    if (index <= 0 || index > list->len) {
        printf("deleteData fucntion param(index) error...return -1\n");
        return -1;
    }

    if (list->len == 0) {
        printf("this list is empty,operater error");
        return 0;
    }else if(list->len == index)
    {
        list->Data[list->len-1] = 0;
        list->len--;
        return 0;
    }

    for (int i=index-1; i < list->len-1; i++) {
        list->Data[i] = list->Data[i+1];
    }
    list->Data[list->len-1] = 0;
    list->len--;

    return 0;
}

int getLen(List list)
{
    return list.len;
}

int clearList(List list)
{

    for (int i=0; i < list.len; i++) {
        list.Data[i] = 0;
    }
    list.len = 0;
    return 0;
}

int getListData(List list, int index)
{
    if (index <= 0 || index > list.len) {
        printf("getListData fucntion param(index) error...return -1\n");
        return -1;
    }
    return list.Data[index-1];
}

int showList(List list)
{
    if (list.len == 0) {
        printf("this list is empty\n");
        return 0;
    }
    for (int i=0; i<list.len; i++) {
        printf("%d ",list.Data[i]);
    }
    printf("\n");
    return 0;
}

线性表的链式存储结构 带头结点 单链表

#include "stdio.h"
#include "string.h"
#include "ctype.h"
#include "stdlib.h"
#include "math.h"
#include "time.h"


typedef struct Node{
    int data; // 数据域
    struct Node* next; // 指针域
} Node;

typedef struct Node* LinkList;


//初始化线性表
int initList(LinkList* list);
//线性表是否为空
int isEmpty(LinkList list);
//清空线性表
int clearList(LinkList list);
//线性表的长度
int getListLen(LinkList list);
//获取线性表的元素
int getListData(LinkList list, int index);
//判断元素是否在线性表中
int dataIsList(LinkList list, int value);
//插入元素
int insertDataInList(LinkList* list, int index, int value);
//删除元素
int deleteDataInList(LinkList* list, int index);
//打印链表
int showList(LinkList list);
//随机产生n个元素的值,建立带头节点的单链表(头插法)
int createListFirst(LinkList* list,int n);
//随机产生n个元素的值,建立带头节点的单链表(尾插法)
int createListEnd(LinkList* list, int n);

//初始化线性表 实际上就是创建了一个头结点
int initList(LinkList* list)
{
    *list = (LinkList)malloc(sizeof(Node)); // 产生头结点
    if (!(*list)) {
        printf("init linklist error.\n");
        return -1;
    }
    (*list)->next = NULL;

    return 0;
}
//线性表是否为空
int isEmpty(LinkList list)
{
    if (list->next) {
        printf("this list not empty\n");
    }else{
        printf("this list is empty\n");
    }
    return 0;
}
//清空线性表
int clearList(LinkList list)
{
    printf("clear this list \n");
    LinkList l = list->next;
    LinkList p;
    while (l) {
        p = l;
        free(l);
        l->next = NULL;
        l = p->next;
    }
    list->next = NULL;
    return 0;
}
//线性表的长度
int getListLen(LinkList list)
{
    LinkList l = list->next;
    int i=0;
    while (l) {
        i++;
        l = l->next;
    }
    return i;
}
//获取线性表的元素
int getListData(LinkList list, int index)
{
    int len = getListLen(list);
    if (index > len) {
        printf("function getListData param(index) more than list len....index = %d len = %d\n",index,len);
        return -1;
    }
    LinkList l = list->next;
    int num = 1;
    while (l && num < index) {
        l = l->next;
        num++;
    }

    return l->data;
}
//判断元素是否在线性表中
int dataIsList(LinkList list, int value)
{
    LinkList l = list->next;
    while (l) {
        if (l->data == value) {
            printf("the data(%d) exist the list\n",value);
            return 0;
        }
        l = l->next;
    }
    printf("dont exist this data(%d) in list\n",value);
    return 0;
}
//插入元素 在list链表中index位置,插入元素value
int insertDataInList(LinkList* list, int index, int value)
{
    // 当链表没有节点的时候,就是表头,
    // 当index为链表长度是,插在最末。
    int j=1;
    int len = getListLen(*list);
    LinkList newNode,newlist;
    newlist = (*list);

    newNode = (LinkList)malloc(sizeof(Node));
    newNode->data = value;

//    printf("\n");
    if (getListLen(*list) == 0) {
//        printf("11111111111111111111111\n");
        newlist->next = newNode;
        newlist = newNode;
        newlist->next = NULL;
    }else if(index >=getListLen(*list) ){
//        printf("22222222222222222222222 value = %d,len = %d,index = %d\n",value,len,index);

        while (1) {
            newlist = newlist->next;
            if (j == len)
            {
                break;
            }
            j++;
        }
//        printf("while after nowNode = %d\n",newlist->data);
        newlist->next = newNode;
        newlist = newNode;
        newlist->next = NULL;
    }else{
//        printf("333333333333333333333333 value = %d,len = %d,index = %d\n",value,len,index);
        while (1) {
            newlist = newlist->next;
            if (j == index) {
                break;
            }
            j++;
        }
//        printf("while after nowNode = %d\n",newlist->data);
        // 先接起来,在断开
        newNode->next = newlist->next;
        newlist->next = newNode;
    }
    return 0;
}

//删除元素
int deleteDataInList(LinkList* list, int index)
{
    int len = getListLen(*list);
    int num = 0;
    LinkList l = (*list)->next;

    if (index > len) {
        printf("function deleteDataInList param(index) more than list len....index = %d len = %d\n",index,len);
        index = len;
    }
    if (index == 1 || index == 0) {
        (*list)->next = (*list)->next->next;
        return 0;
    }

    while (l && num < index-2) {
        l = l->next;
        num++;
    }

    printf("delete data is %d\n",l->next->data);
    free(l->next);
    l->next = l->next->next;
    return 0;
}
//打印链表
int showList(LinkList list)
{
    LinkList l = list->next;
    printf("list have data : ");
    while (l) {
        printf("%d ",l->data);
        l = l->next;
    }
    printf("\n");
    return 0;
}
//随机产生n个元素的值,建立带头节点的单链表(头插法)
int createListFirst(LinkList* list,int n)
{
    LinkList l;
    int i;
    srand(time(0));
    *list = (LinkList)malloc(sizeof(Node));
    (*list)->next = NULL;
    for (i = 0; i<n; i++) {
        l = (LinkList)malloc(sizeof(Node));
        l->data = rand()%100;
        l->next = (*list)->next;
        (*list)->next = l;
        printf("%d ",l->data);
    }
    printf("\n");
    return 0;
}
//随机产生n个元素的值,建立带头节点的单链表(尾插法)
int createListEnd(LinkList* list, int n)
{
    LinkList l,r;
    int i;
    srand(time(0));
    *list = (LinkList)malloc(sizeof(Node));
    r = *list;
    for (i=0; i<n;i++) {
        l = (LinkList)malloc(sizeof(Node));
        l->data = rand()%100;
        r->next = l;
        r = l;
        printf("%d ",l->data);
    }
    printf("\n");
    r->next = NULL;
    return 0;
}

int main1()
{
    LinkList linklist; // 这个就是头结点
    linklist->next = NULL;

    isEmpty(linklist);

    int ret = initList(&linklist);
    if (ret != 0) {
        printf("function initList error... %d \n",ret);
    }
    for (int i=1; i<6; i++) {
        ret = insertDataInList(&linklist, 1, i);
        showList(linklist);
    }

    showList(linklist);                             // 1 5 4 3 2
    int len = getListLen(linklist);
    printf("this list len is : %d\n",len);          // 5
    deleteDataInList(&linklist, 2);                 // 5
    showList(linklist);                             // 1 4 3 2

    deleteDataInList(&linklist, 0);                 // 1
    showList(linklist);                             // 4 3 2

    deleteDataInList(&linklist, 10);                // 2
    showList(linklist);                             // 4 3

    int data = getListData(linklist,4);
    if (data == -1)
    {
        printf("function getListData error\n");
    }else{
        printf("get data is %d\n",data);                // 2
    }

    dataIsList(linklist,30);                        // dont exist


    clearList(linklist);
    isEmpty(linklist);
    int len1 = getListLen(linklist);
    printf("this list len is : %d\n",len1);
    return 0;
}
//  验证头插法和尾插法
int main2()
{
    LinkList l;
    initList(&l);
    createListFirst(&l, 10);
    showList(l);

    LinkList p;
    initList(&p);
    createListEnd(&p, 10);
    showList(p);
    return 0;
}

线性表的链式存储结构 带头结点 循环链表

#include "stdio.h"
#include "math.h"
#include "stdlib.h"


typedef struct Node{
    int data; // 数据域
    struct Node* next; // 指针域
} Node;

typedef struct Node* LinkList;


//初始化线性表
int initList(LinkList* list);
//线性表是否为空
int isEmpty(LinkList list);
//清空线性表
int clearList(LinkList list);
//线性表的长度
int getListLen(LinkList list);
//获取线性表的元素
int getListData(LinkList list, int index);
//判断元素是否在线性表中
int dataIsList(LinkList list, int value);
//插入元素
int insertDataInList(LinkList* list, int index, int value);
//删除元素
int deleteDataInList(LinkList* list, int index);
//打印链表
int showList(LinkList list);
//打印链表 用于确定是否是循环链表
int showList_1(LinkList list,int index);

int main()
{
    LinkList linklist; // 这个就是头结点
    linklist->next = NULL;

    int ret = initList(&linklist);
    if (ret != 0) {
        printf("function initList error... %d \n",ret);
    }
    for (int i=1; i<6; i++) {
        ret = insertDataInList(&linklist, 1, i);
    }

//    showList(linklist);                             // 1 5 4 3 2
    showList_1(linklist,2);

    return 0;
}


//初始化线性表 实际上就是创建了一个头结点
int initList(LinkList* list)
{
    *list = (LinkList)malloc(sizeof(Node)); // 产生头结点
    if (!(*list)) {
        printf("init linklist error.\n");
        return -1;
    }
    (*list)->next = NULL;

    return 0;
}
//线性表是否为空
int isEmpty(LinkList list)
{
    if (list->next) {
        printf("this list not empty\n");
    }else{
        printf("this list is empty\n");
    }
    return 0;
}
//清空线性表
int clearList(LinkList list)
{
    printf("clear this list \n");
    LinkList l = list->next;
    LinkList p;
    while (l) {
        p = l;
        free(l);
        l->next = NULL;
        l = p->next;
    }
    list->next = NULL;
    return 0;
}
//线性表的长度
int getListLen(LinkList list)
{
    LinkList l = list->next;
    int i=0;
    while (1) {

        if (l == list || l == NULL) {
            break;
        }
        l = l->next;
        i++;
    }
    return i;
}
//获取线性表的元素
int getListData(LinkList list, int index)
{
    int len = getListLen(list);
    if (index > len) {
        printf("function getListData param(index) more than list len....index = %d len = %d\n",index,len);
        return -1;
    }
    LinkList l = list->next;
    int num = 1;
    while (l && num < index) {
        l = l->next;
        num++;
    }

    return l->data;
}
//判断元素是否在线性表中
int dataIsList(LinkList list, int value)
{
    LinkList l = list->next;
    while (l) {
        if (l->data == value) {
            printf("the data(%d) exist the list\n",value);
            return 0;
        }
        l = l->next;
    }
    printf("dont exist this data(%d) in list\n",value);
    return 0;
}
//插入元素 在list链表中index位置,插入元素value
int insertDataInList(LinkList* list, int index, int value)
{
    // 当链表没有节点的时候,就是表头,
    // 当index为链表长度是,插在最末。
    int j=1;
    int len = getListLen(*list);
    LinkList newNode,newlist;
    newlist = (*list);

    newNode = (LinkList)malloc(sizeof(Node));
    newNode->data = value;

    //    printf("\n");
    if (len == 0) {
        //        printf("11111111111111111111111\n");
        newlist->next = newNode;
        newlist = newNode;
        newlist->next = *list;
    }else if(index >=len ){
        //        printf("22222222222222222222222 value = %d,len = %d,index = %d\n",value,len,index);

        while (1) {
            newlist = newlist->next;
            if (j == len)
            {
                break;
            }
            j++;
        }
        //        printf("while after nowNode = %d\n",newlist->data);
        newlist->next = newNode;
        newlist = newNode;
        newlist->next = *list;
    }else{
        //        printf("333333333333333333333333 value = %d,len = %d,index = %d\n",value,len,index);
        while (1) {
            newlist = newlist->next;
            if (j == index) {
                break;
            }
            j++;
        }
        //        printf("while after nowNode = %d\n",newlist->data);
        // 先接起来,在断开
        newNode->next = newlist->next;
        newlist->next = newNode;
    }
    return 0;
}

//删除元素
int deleteDataInList(LinkList* list, int index)
{
    int len = getListLen(*list);
    int num = 0;
    LinkList l = (*list)->next;

    if (index > len) {
        printf("function deleteDataInList param(index) more than list len....index = %d len = %d\n",index,len);
        index = len;
    }
    if (index == 1 || index == 0) {
        (*list)->next = (*list)->next->next;
        return 0;
    }

    while (l && num < index-2) {
        l = l->next;
        num++;
    }

    printf("delete data is %d\n",l->next->data);
    free(l->next);
    l->next = l->next->next;
    return 0;
}
//打印链表
int showList(LinkList list)
{
    LinkList l = list->next;
    printf("list have data : ");
    while (l != list) {
        printf("%d ",l->data);
        l = l->next;
    }
    printf("\n");
    return 0;
}
//打印链表 用于确定是否是循环链表
int showList_1(LinkList list, int index)  // index = 2
{
    int j=1;
    LinkList l = list->next;
    printf("list have data : ");
    while (1) {

        if (j == index) {
            break;
        }
        j++;
        l = l->next;
    }
    int tmp = l->data;
    while (1) {

        l = l->next;
        if (l != list) {
            printf("%d ",l->data);
        }
        if (tmp == l->data) {
            break;
        }
    }

    printf("\n");
    return 0;
}
#include "stdio.h"
#include "math.h"
#include "stdlib.h"




// 线性表的链式存储结构 带头结点   双向链表
typedef struct Node{
    int data; // 数据域
    struct Node* prior; //直接前驱指针
    struct Node* next; //直接后继指针
} Node;

typedef struct Node* LinkList;


//初始化线性表
int initList(LinkList* list);       //ok
//线性表的长度
int getListLen(LinkList list);      //ok
//插入元素
int insertDataInList(LinkList* list, int index, int value);      //ok
//删除元素
int deleteDataInList(LinkList* list, int index);      //ok
//打印链表
int showList(LinkList list);    //ok

int main()
{
    LinkList linklist; // 这个就是头结点
    linklist->next = NULL;

    int ret = initList(&linklist);
    if (ret != 0) {
        printf("function initList error... %d \n",ret);
    }
    for (int i=1; i<6; i++) {
        ret = insertDataInList(&linklist, 1, i);
        showList(linklist);
    }
    deleteDataInList(&linklist, 30);
    showList(linklist);


    return 0;
}


//初始化线性表 实际上就是创建了一个头结点
int initList(LinkList* list)
{
    *list = (LinkList)malloc(sizeof(Node)); // 产生头结点
    if (!(*list)) {
        printf("init linklist error.\n");
        return -1;
    }
    (*list)->next = NULL;
    (*list)->prior = NULL;

    return 0;
}
//线性表是否为空
int isEmpty(LinkList list)
{
    if (list->next) {
        printf("this list not empty\n");
    }else{
        printf("this list is empty\n");
    }
    return 0;
}
//清空线性表
int clearList(LinkList list)
{
    printf("clear this list \n");
    LinkList l = list->next;
    LinkList p;
    while (l) {
        p = l;
        free(l);
        l->next = NULL;
        l = p->next;
    }
    list->next = NULL;
    return 0;
}
//线性表的长度
int getListLen(LinkList list)
{
    LinkList l = list->next;
    int i=0;
    while (1) {

        if (l == list || l == NULL) {  // l == list 是处理循环链表的条件
            break;
        }
        l = l->next;
        i++;
    }
    return i;
}
//获取线性表的元素
int getListData(LinkList list, int index)
{
    int len = getListLen(list);
    if (index > len) {
        printf("function getListData param(index) more than list len....index = %d len = %d\n",index,len);
        return -1;
    }
    LinkList l = list->next;
    int num = 1;
    while (l && num < index) {
        l = l->next;
        num++;
    }

    return l->data;
}
//判断元素是否在线性表中
int dataIsList(LinkList list, int value)
{
    LinkList l = list->next;
    while (l) {
        if (l->data == value) {
            printf("the data(%d) exist the list\n",value);
            return 0;
        }
        l = l->next;
    }
    printf("dont exist this data(%d) in list\n",value);
    return 0;
}
//插入元素 在list链表中index位置,插入元素value
int insertDataInList(LinkList* list, int index, int value)
{
    LinkList l = (*list);
    LinkList newNode = (LinkList)malloc(sizeof(Node));
    newNode->data = value;
    newNode->prior = NULL;
    newNode->next = NULL;
    int j = 1;
    int len = getListLen(*list);
//        printf("\n");
    if (len == 0) {
//        printf("11111111111111111111111\n");
        l->next = newNode;
        newNode->prior = l;
        newNode->next = NULL;
    }else if(index >=len ){
//        printf("22222222222222222222222 value = %d,len = %d,index = %d\n",value,len,index);
        while (1) {
            l = l->next;
            if (j == len) {
                break;
            }

            j++;
        }
//        printf("l->data = %d ,j=%d ",l->data,j);
        l->next = newNode;
        newNode->prior = l;
        newNode->next = NULL;
    }else{
//        printf("333333333333333333333333 value = %d,len = %d,index = %d\n",value,len,index);
        while (1) {
            l = l->next;
            if (j == index) {
                break;
            }

            j++;
        }
//        printf("l->data = %d ,j=%d ",l->data,j);
        newNode->prior = l;
        newNode->next = l->next;
        l->next->prior = newNode;
        l->next = newNode;
    }
//    printf("\n");
    return 0;
}

//删除元素
int deleteDataInList(LinkList* list, int index)
{
    int len = getListLen(*list);
    int num = 0;
    LinkList l = (*list);

    if (index > len) {
        printf("function deleteDataInList param(index) more than list len....index = %d len = %d\n",index,len);
        index = len;
    }
    if (index == 1 || index == 0) {
        printf("delete data is %d\n",l->next->data);
        l->next = l->next->next;
        l->next->next->prior = l;
        return 0;
    }

    while (l && num < index-2) {
        l = l->next;
        num++;
    }

    printf("delete data is %d\n",l->next->data);
    l->next->next->prior = l;
    l->next = l->next->next;
    return 0;
}
//打印链表
int showList(LinkList list)
{
    LinkList l = list->next;
    printf("list have data : ");
    while (l) {
        printf("%d ",l->data);
        l = l->next;
    }
    printf("\n");
    return 0;
}
//打印链表 用于确定是否是循环链表
int showList_1(LinkList list, int index)  // index = 2
{
    int j=1;
    LinkList l = list->next;
    printf("list have data : ");
    while (1) {

        if (j == index) {
            break;
        }
        j++;
        l = l->next;
    }
    int tmp = l->data;
    while (1) {

        l = l->next;
        if (l != list) {
            printf("%d ",l->data);
        }
        if (tmp == l->data) {
            break;
        }
    }

    printf("\n");
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值