学习记录day16—— 数据结构 双向链表 循环链表

双向链表

1、概念

1)就是从任意一个节点既能存储其前驱节点,又能存储后继节点

2)结构体中增加一个指向前驱节点的指针

//定义数据类型
typedef int datatype;
 
//定义节点类型
typedef struct Node
{
    union 
    {
        int len;
        datatype data;
    };
    struct Node *prio; 
    
    struct Node *next; 
    
};

3)头节点没有前驱,最后一个节点没有后继

2、创建虚拟链表

// 创建链表
NodePtr list_create()
{
    // 在堆区申请一个头节点
    NodePtr L = (NodePtr)malloc(sizeof(Node));
    if (NULL == L)
    {
        printf("创建失败\n");
        return NULL;
    }

    L->len = 0;
    L->next = NULL;
    L->prio = NULL;

    printf("链表创建成功\n");
    return L;
}

3、申请封装数据

// 申请封装数据
NodePtr apply_node(datatype e)
{
    NodePtr p = (NodePtr)malloc(sizeof(Node));
    if (NULL == p)
    {
        printf("数据类型不合法,封装失败\n");
        return NULL;
    }

    p->data = e;
    p->prio = NULL;
    p->next = NULL;

    return p;
}

4、判空

// 判空
int list_empty(NodePtr L)
{
    return L->next == NULL;
}

5、头插

// 头插
int list_insert_head(NodePtr L, datatype e)
{
    if (NULL == L)
    {
        printf("数据类型不合法,头插失败\n");
        return -1;
    }

    NodePtr p = apply_node(e);
    if (NULL == p)
    {
        printf("数据封装失败,头插失败\n");
        return -1;
    }

    if (list_empty(L))
    {
        p->prio = L;
        L->next = p;
    }
    else
    {
        p->prio = L;
        p->next =  L->next;

        L->next->prio = p; // p->next->prio =p;
        L->next = p;
    }

    L->len++;

    printf("插入成功\n");
    return 0;
}

6、链表遍历

// 链表遍历
int list_show(NodePtr L)
{
    if (NULL == L || list_empty(L))
    {
        printf("遍历失败\n");
        return -1;
    }

    NodePtr q = L->next; // 定义遍历指针从第一个节点出发
    while (q)
    {
        // 输出数据域
        printf("%c", q->data);

        q = q->next; // 指针指向下一数据域
    }
    putchar(10);
    printf("遍历结束\n");
}

7、按完整查找

// 按位置查找
NodePtr list_search_pos(NodePtr L,datatype pos)
{
    if (NULL == L || list_empty(L) || pos > L->len || pos < 0)
    {
        printf("查找失败\n");
        return NULL;
    }

    NodePtr q = L;

    for(int i = 0;i < pos ; i++)
    {
        q = q->next;
    }

    printf("查找成功\n");
    return q;
}

8、按位置删除

// 按位置删除
int list_delete_pos(NodePtr L,datatype pos)
{
    if (NULL == L || list_empty(L) || pos < 1 || pos > L->len)
    {
        printf("按位置删除失败\n");
        return -1;
    }

    NodePtr q = list_search_pos(L,pos);

    if (q->next == NULL)
    {
        q->prio->next = NULL;

    }
    else
    {
        // q->next->prio = q->prio;
        // q->next->prio->next = q->next;

        q->prio->next = q->next;
        q->next->prio = q->prio;
        

    }
    L->len--;
    free(q);
    q = NULL;

    printf("删除成功\n");
    return 0;
}

9、链表删除

// 链表删除
void list_destroy(NodePtr L)
{
    if (NULL == L )
    {
        printf("删除失败\n");
        return;
    }
    
    while (L->next/*!(list_empty(L))*/)
    {
        list_delete_pos(L,1);
    }
    
    if (L->next = NULL)
    {
        free(L);
        L->next = NULL;
    }
    
    printf("删除成功\n");
    return ;
}

10、完整代码

00.h

#ifndef day16_flag_h
#define day16_flag_h
#include <myhead.h>

typedef char datatype;

typedef struct Node
{
    union 
    {
        int len;
        datatype data;
    };

    struct Node *prio;
    struct Node *next;
    
}Node,*NodePtr;

NodePtr list_create();

int  list_empty(NodePtr L);

NodePtr apply_node(datatype e);

int  list_insert_head(NodePtr l,datatype e);

int list_show(NodePtr L);

int list_search(NodePtr L,datatype pos);

int list_delete_pos(NodePtr L,datatype e);

void list_destroy(NodePtr L);

#endif // day16_flag_h

00.c

#include "00.h"
#define MAX 50

// 创建链表
NodePtr list_create()
{
    // 在堆区申请一个头节点
    NodePtr L = (NodePtr)malloc(sizeof(Node));
    if (NULL == L)
    {
        printf("创建失败\n");
        return NULL;
    }

    L->len = 0;
    L->next = NULL;
    L->prio = NULL;

    printf("链表创建成功\n");
    return L;
}

// 判空
int list_empty(NodePtr L)
{
    return L->next == NULL;
}

// 申请封装数据
NodePtr apply_node(datatype e)
{
    NodePtr p = (NodePtr)malloc(sizeof(Node));
    if (NULL == p)
    {
        printf("数据类型不合法,封装失败\n");
        return NULL;
    }

    p->data = e;
    p->prio = NULL;
    p->next = NULL;

    return p;
}

// 头插
int list_insert_head(NodePtr L, datatype e)
{
    if (NULL == L)
    {
        printf("数据类型不合法,头插失败\n");
        return -1;
    }

    NodePtr p = apply_node(e);
    if (NULL == p)
    {
        printf("数据封装失败,头插失败\n");
        return -1;
    }

    if (list_empty(L))
    {
        p->prio = L;
        L->next = p;
    }
    else
    {
        p->prio = L;
        p->next =  L->next;

        L->next->prio = p; // p->next->prio =p;
        L->next = p;
    }

    L->len++;

    printf("插入成功\n");
    return 0;
}


// 链表遍历
int list_show(NodePtr L)
{
    if (NULL == L || list_empty(L))
    {
        printf("遍历失败\n");
        return -1;
    }

    NodePtr q = L->next; // 定义遍历指针从第一个节点出发
    while (q)
    {
        // 输出数据域
        printf("%c", q->data);

        q = q->next; // 指针指向下一数据域
    }
    putchar(10);
    printf("遍历结束\n");
}

// 按位置查找
NodePtr list_search_pos(NodePtr L,datatype pos)
{
    if (NULL == L || list_empty(L) || pos > L->len || pos < 0)
    {
        printf("查找失败\n");
        return NULL;
    }

    NodePtr q = L;

    for(int i = 0;i < pos ; i++)
    {
        q = q->next;
    }

    printf("查找成功\n");
    return q;
}

// 按位置删除
int list_delete_pos(NodePtr L,datatype pos)
{
    if (NULL == L || list_empty(L) || pos < 1 || pos > L->len)
    {
        printf("按位置删除失败\n");
        return -1;
    }

    NodePtr q = list_search_pos(L,pos);

    if (q->next == NULL)
    {
        q->prio->next = NULL;

    }
    else
    {
        // q->next->prio = q->prio;
        // q->next->prio->next = q->next;

        q->prio->next = q->next;
        q->next->prio = q->prio;
        

    }
    L->len--;
    free(q);
    q = NULL;

    printf("删除成功\n");
    return 0;
}

// 链表删除
void list_destroy(NodePtr L)
{
    if (NULL == L )
    {
        printf("删除失败\n");
        return;
    }
    
    while (L->next/*!(list_empty(L))*/)
    {
        list_delete_pos(L,1);
    }
    
    if (L->next = NULL)
    {
        free(L);
        L->next = NULL;
    }
    
    printf("删除成功\n");
    return ;
}

00main.c

#include "00.h"

int main(int argc, char const *argv[])
{
    NodePtr L = list_create();
    if (NULL == L )
    {
        return -1;
    }
    
    list_insert_head(L,'H');
    list_show(L);
    list_insert_head(L,'e');
    list_show(L);
    list_insert_head(L,'l');
    list_show(L);
    list_insert_head(L,'l');
    list_show(L);
    list_insert_head(L,'o');
    list_show(L);

    list_delete_pos(L,1);
    list_show(L);
    list_delete_pos(L,2);
    list_show(L);
    list_delete_pos(L,L->len);
    list_show(L);

    list_destroy(L);
    list_show(L);
    return 0;
}

单向循环链表

1、概念

1)循环链表,就是首尾相接的链表

2)循环链表,就是首尾相接的链表

3)双向循环链表:需要将最后一个阶段的指针域指向头结点,头结点的前驱指针指向最后一 个阶段

2、循环链表的创建

1)创建虚拟链表

// 创建链表
NodePtr list_create()
{
    // 在堆区申请一个头节点
    NodePtr L = (NodePtr)malloc(sizeof(Node));
    if (NULL == L)
    {
        printf("创建失败\n");
        return NULL;
    }

    L->len = 0;
    L->next = NULL;
    L->prio = NULL;

    printf("链表创建成功\n");
    return L;
}

2)判空

// 判空
int list_empty(NodePtr L)
{
    return L->next == L;
}

3)申请封装数据

// 申请封装数据
NodePtr apply_node(datatype e)
{
    NodePtr p = (NodePtr)malloc(sizeof(Node));
    if (NULL == p)
    {
        printf("数据类型不合法,封装失败\n");
        return NULL;
    }

    p->data = e;
    p->next = NULL;

    return p;
}

4)按位置查找

// 按位置查找
NodePtr list_search_pos(NodePtr L, datatype pos)
{
    if (NULL == L || list_empty(L) || pos > L->len || pos < 0)
    {
        printf("查找失败\n");
        return NULL;
    }

    NodePtr q = L;

    for (int i = 0; i < pos; i++)
    {
        q = q->next;
    }

    printf("查找成功\n");
    return q;
}

5)头插

// 头插
int list_insert_head(NodePtr L, datatype e)
{
    // 判断逻辑
    if (NULL == L)
    {
        printf("插入失败\n");
        return -1;
    }

    NodePtr p = apply_node(e);
    if (NULL == p)
    {
        printf("封装失败\n");
        return -1;
    }

    p->next = L->next;
    L->next = p;

    L->len++;

    printf("插入成功\n");
    return 0;
}

6)尾插

// 尾插
int list_insert_tail(NodePtr L, datatype e)
{
    // 判断逻辑
    if (NULL == L)
    {
        printf("尾插插入失败\n");
        return -1;
    }

    // 找到最后一个节点
    NodePtr q = list_search_pos(L, L->len);

    // 封装节点
    NodePtr p = apply_node(e);

    // 插入逻辑
    p->next = q->next;
    q->next = p;

    L->len++;

    printf("尾插插入成功\n");

    return 0;
}

7)头删

//头删
int list_delete_head(NodePtr L)
{
    if (NULL == L || list_empty(L))
    {
        printf("头删失败\n");
        return -1;
    }
    
    NodePtr p = L->next;
    L->next = p->next;
    free(p);
    p = NULL;

    L->len--;

    printf("头删成功\n");
    return 0;
}

8)链表删除

// 链表删除
void list_destroy(NodePtr L)
{
    if (NULL == L )
    {
        printf("删除失败\n");
        return;
    }
    
    while (L->next == L)
    {
        list_delete_head(L);
    }
    

    free(L);
    L = NULL;
    
    printf("删除成功\n");
    return ;
}

9)完整代码

00.h

#ifndef day16_1_flag_h
#define day16_1_flag_h
#include <myhead.h>

typedef char datatype;

typedef struct Node
{
    union 
    {
        int len;
        datatype data;
    };

    struct Node *next;
    
}Node,*NodePtr;

NodePtr list_create();

int  list_empty(NodePtr L);

NodePtr apply_node(datatype e);

NodePtr list_search_pos(NodePtr L,datatype pos);

int list_insert_tail(NodePtr L,datatype e);

int list_insert_head(NodePtr L,datatype e);

int list_show(NodePtr L);

int list_delete_head(NodePtr L);

void list_destroy(NodePtr L);

#endif // day16_1_flag_h

00.c

#include "00.h"
#define MAX 50

// 创建链表
NodePtr list_create()
{
    // 在堆区申请一个头节点
    NodePtr L = (NodePtr)malloc(sizeof(Node));
    if (NULL == L)
    {
        printf("创建失败\n");
        return NULL;
    }

    L->len = 0;
    L->next = L; // 头节点指针域指向自己

    printf("链表创建成功\n");
    return L;
}

// 判空
int list_empty(NodePtr L)
{
    return L->next == L;
}

// 申请封装数据
NodePtr apply_node(datatype e)
{
    NodePtr p = (NodePtr)malloc(sizeof(Node));
    if (NULL == p)
    {
        printf("数据类型不合法,封装失败\n");
        return NULL;
    }

    p->data = e;
    p->next = NULL;

    return p;
}

// 按位置查找
NodePtr list_search_pos(NodePtr L, datatype pos)
{
    if (NULL == L || list_empty(L) || pos > L->len || pos < 0)
    {
        printf("查找失败\n");
        return NULL;
    }

    NodePtr q = L;

    for (int i = 0; i < pos; i++)
    {
        q = q->next;
    }

    printf("查找成功\n");
    return q;
}

// 头插
int list_insert_head(NodePtr L, datatype e)
{
    // 判断逻辑
    if (NULL == L)
    {
        printf("插入失败\n");
        return -1;
    }

    NodePtr p = apply_node(e);
    if (NULL == p)
    {
        printf("封装失败\n");
        return -1;
    }

    p->next = L->next;
    L->next = p;

    L->len++;

    printf("插入成功\n");
    return 0;
}

// 尾插
int list_insert_tail(NodePtr L, datatype e)
{
    // 判断逻辑
    if (NULL == L)
    {
        printf("尾插插入失败\n");
        return -1;
    }

    // 找到最后一个节点
    NodePtr q = list_search_pos(L, L->len);

    // 封装节点
    NodePtr p = apply_node(e);

    // 插入逻辑
    p->next = q->next;
    q->next = p;

    L->len++;

    printf("尾插插入成功\n");

    return 0;
}

//链表遍历
int list_show(NodePtr L)
{
    if (NULL == L || list_empty(L))
    {
        printf("遍历失败\n");
        return -1;
    }

    NodePtr q = L->next;

    while(q !=L)
    {
        printf("%c",q->data);
        q = q->next;
    }
    putchar(10);
    printf("遍历成功\n");

    return 0;
}

//头删
int list_delete_head(NodePtr L)
{
    if (NULL == L || list_empty(L))
    {
        printf("头删失败\n");
        return -1;
    }
    
    NodePtr p = L->next;
    L->next = p->next;
    free(p);
    p = NULL;

    L->len--;

    printf("头删成功\n");
    return 0;
}

// 链表删除
void list_destroy(NodePtr L)
{
    if (NULL == L )
    {
        printf("删除失败\n");
        return;
    }
    
    while (L->next == L)
    {
        list_delete_head(L);
    }
    

    free(L);
    L = NULL;
    
    printf("删除成功\n");
    return ;
}

00main.c

#include "00.h"

int main(int argc, char const *argv[])
{
    NodePtr L = list_create();
    if (NULL == L )
    {
        return -1;
    }
    
    list_insert_head(L,'H');
    list_show(L);
    list_insert_head(L,'e');
    list_show(L);
    list_insert_head(L,'l');
    list_show(L);
    list_insert_head(L,'l');
    list_show(L);
    list_insert_head(L,'o');
    list_show(L);

    list_insert_tail(L,'Z');
    list_show(L);

    list_delete_head(L);
    list_show(L);

    list_destroy(L);
    list_show(L);
    return 0;
}

10)约瑟夫环问题

00.h

#ifndef day16_1_flag_h
#define day16_1_flag_h
#include <myhead.h>

typedef int datatype;

typedef struct Node
{
    union 
    {
        int len;
        datatype data;
    };

    struct Node *next;
    
}Node,*NodePtr;

NodePtr list_create();

int  list_empty(NodePtr L);

NodePtr apply_node(datatype e);

NodePtr list_search_pos(NodePtr L,datatype pos);

int list_insert_tail(NodePtr L,datatype e);

int list_insert_head(NodePtr L,datatype e);

int list_show(NodePtr L);

int list_delete_head(NodePtr L);

void list_destroy(NodePtr L);

// 任意位置删除
int list_delete_pos(NodePtr L, int pos);

//按位置取值
int list_pos_value(NodePtr L,int pos);
#endif // day16_1_flag_h

00.c

#include "00.h"
#define MAX 50

// 创建链表
NodePtr list_create()
{
    // 在堆区申请一个头节点
    NodePtr L = (NodePtr)malloc(sizeof(Node));
    if (NULL == L)
    {
        printf("创建失败\n");
        return NULL;
    }

    L->len = 0;
    L->next = L; // 头节点指针域指向自己

    printf("链表创建成功\n");
    return L;
}

// 判空
int list_empty(NodePtr L)
{
    return L->next == L;
}

// 申请封装数据
NodePtr apply_node(datatype e)
{
    NodePtr p = (NodePtr)malloc(sizeof(Node));
    if (NULL == p)
    {
        printf("数据类型不合法,封装失败\n");
        return NULL;
    }

    p->data = e;
    p->next = NULL;

    return p;
}

// 按位置查找
NodePtr list_search_pos(NodePtr L, datatype pos)
{
    if (NULL == L || list_empty(L) || pos > L->len || pos < 0)
    {
        printf("查找失败\n");
        return NULL;
    }

    NodePtr q = L;

    for (int i = 0; i < pos; i++)
    {
        q = q->next;
    }

    printf("查找成功\n");
    return q;
}

// 头插
int list_insert_head(NodePtr L, datatype e)
{
    // 判断逻辑
    if (NULL == L)
    {
        printf("插入失败\n");
        return -1;
    }

    NodePtr p = apply_node(e);
    if (NULL == p)
    {
        printf("封装失败\n");
        return -1;
    }

    p->next = L->next;
    L->next = p;

    L->len++;

    printf("插入成功\n");
    return 0;
}

// 尾插
int list_insert_tail(NodePtr L, datatype e)
{
    // 判断逻辑
    if (NULL == L)
    {
        printf("尾插插入失败\n");
        return -1;
    }

    // 找到最后一个节点
    NodePtr q = list_search_pos(L, L->len);

    // 封装节点
    NodePtr p = apply_node(e);

    // 插入逻辑
    p->next = q->next;
    q->next = p;

    L->len++;

    printf("尾插插入成功\n");

    return 0;
}

//链表遍历
int list_show(NodePtr L)
{
    if (NULL == L || list_empty(L))
    {
        printf("遍历失败\n");
        return -1;
    }

    NodePtr q = L->next;

    while(q !=L)
    {
        printf("%d\t",q->data);
        q = q->next;
    }
    putchar(10);
    printf("遍历成功\n");

    return 0;
}

//头删
int list_delete_head(NodePtr L)
{
    if (NULL == L || list_empty(L))
    {
        printf("头删失败\n");
        return -1;
    }
    
    NodePtr p = L->next;
    L->next = p->next;
    free(p);
    p = NULL;

    L->len--;

    printf("头删成功\n");
    return 0;
}

// 链表删除
void list_destroy(NodePtr L)
{
    if (NULL == L )
    {
        printf("删除失败\n");
        return;
    }
    
    while (L->next == L)
    {
        list_delete_head(L);
    }
    

    free(L);
    L = NULL;
    
    printf("删除成功\n");
    return ;
}

// 任意位置删除
int list_delete_pos(NodePtr L, int pos)
{
    if (NULL == L || pos > L->len + 1 || pos < 1)
    {
        printf("删除失败\n");
        return -1;
    }

    NodePtr q = list_search_pos(L, pos - 1);

    NodePtr p = q->next;
    q->next = p->next;
    free(p);
    p = NULL;

    L->len--;
    printf("删除成功\n");
    return 0;
}

00main.c

#include "00.h"

int main(int argc, char const *argv[])
{
    //创建列表
    NodePtr L = list_create();
    if (NULL == L)
    {
        return -1;
    }

    //num 人数  die 死亡序号
    int num, die = 0;
    
    printf("输入参与约瑟夫游戏的人数:\n");
    scanf("%d", &num);
    printf("报数到多少被杀掉:\n");
    scanf("%d", &die);

    //为参与者赋予代号
    for (int i = 0; i < num; i++)
    {
        list_insert_head(L, i+1);
    }

    list_show(L);

    //day 日期   all 总人数   death 死者数组
    int day = 0;
    int all = num;
    datatype death[100] = {0};  //死者序列
    NodePtr p = L;
    while (num>all/2)
    {
        for (int i = 0; i < die-1; i++)
        {
            if (p->next == L)//到头节点时多偏移一位,略过头节点
            {
                p = p->next;
            }
            
            p = p->next;
        }

        int kill = p->next->data;           //死者代号
        death[day] = kill;                  //将死者代号存入死者名列
        printf("%d\n",kill);
        list_delete_head(p->next);          //删除死者位置
        day++;                              //日期推移
        num--;                              //人数减一
    }

    printf("死者代号及顺序依次为:\n");
    for (int i = 0; i < day; i++)
    {
        printf("%d\t", death[i]);
    }
    putchar(10);

    return 0;
}

双向循环链表

00.h

#ifndef day16_1_flag_h
#define day16_1_flag_h
#include <myhead.h>

typedef char datatype;

typedef struct Node
{
    union 
    {
        int len;
        datatype data;
    };

    struct Node *next;
    struct Node *prio;
    
}Node,*NodePtr;

NodePtr list_create();

int  list_empty(NodePtr L);

NodePtr apply_node(datatype e);

NodePtr list_search_pos(NodePtr L,datatype pos);

int list_insert_tail(NodePtr L,datatype e);

int list_insert_head(NodePtr L,datatype e);

int list_show(NodePtr L);

int list_delete_head(NodePtr L);

void list_destroy(NodePtr L);

// 任意位置删除
int list_delete_pos(NodePtr L, int pos);

//按位置取值
int list_pos_value(NodePtr L,int pos);

//按位置修改
int list_change_pos(NodePtr L,int pos,datatype e);
#endif // day16_1_flag_h

00.c

#include "00.h"
#define MAX 50

// 创建链表
NodePtr list_create()
{
    // 在堆区申请一个头节点
    NodePtr L = (NodePtr)malloc(sizeof(Node));
    if (NULL == L)
    {
        printf("创建失败\n");
        return NULL;
    }

    L->len = 0;
    L->next = L; // 头节点指针域指向自己
    L->prio = L;

    printf("链表创建成功\n");

    return L;
}

// 判空
int list_empty(NodePtr L)
{
    return L->next == L;
}

// 申请封装数据
NodePtr apply_node(datatype e)
{
    NodePtr p = (NodePtr)malloc(sizeof(Node));
    if (NULL == p)
    {
        printf("数据类型不合法,封装失败\n");
        return NULL;
    }

    p->data = e;
    p->next = NULL;
    p->prio = NULL;

    return p;
}

// 按位置查找
NodePtr list_search_pos(NodePtr L, datatype pos)
{
    if (NULL == L || list_empty(L) || pos > L->len || pos < 0)
    {
        printf("查找失败\n");
        return NULL;
    }

    NodePtr q = L;

    for (int i = 0; i < pos; i++)
    {
        q = q->next;
    }

    printf("查找成功\n");
    return q;
}

// 头插
int list_insert_head(NodePtr L, datatype e)
{
    if (NULL == L)
    {
        printf("数据类型不合法,头插失败\n");
        return -1;
    }

    NodePtr p = apply_node(e);
    if (NULL == p)
    {
        printf("数据封装失败,头插失败\n");
        return -1;
    }

    if (list_empty(L))
    {
        p->prio = L;
        p->next = L->next; // p->next = L
        L->next = p;
        L->prio = p;
    }
    else
    {
        p->prio = L;
        p->next = L->next;

        L->next->prio = p; // p->next->prio =p;
        L->next = p;
    }

    L->len++;

    printf("插入成功\n");
    return 0;
}

// 尾插
int list_insert_tail(NodePtr L, datatype e)
{
    // 判断逻辑
    if (NULL == L)
    {
        printf("尾插插入失败\n");
        return -1;
    }

    // 找到最后一个节点
    NodePtr q = list_search_pos(L, L->len);

    // 封装节点
    NodePtr p = apply_node(e);

    // 插入逻辑
    p->next = q->next;
    p->prio = q;

    q->next = p;

    L->len++;

    printf("尾插插入成功\n");
    return 0;
}

// 链表遍历
int list_show(NodePtr L)
{
    if (NULL == L || list_empty(L))
    {
        printf("遍历失败\n");
        return -1;
    }

    NodePtr q = L->next;

    while (q != L)
    {
        printf("%c", q->data);
        q = q->next;
    }
    putchar(10);
    printf("遍历成功\n");

    return 0;
}

// 头删
int list_delete_head(NodePtr L)
{
    if (NULL == L || list_empty(L))
    {
        printf("头删失败\n");
        return -1;
    }

    NodePtr p = L->next;
    L->next = p->next;
    p->next->prio = L;
    free(p);
    p = NULL;

    L->len--;

    printf("头删成功\n");

    return 0;
}

// 链表删除
void list_destroy(NodePtr L)
{
    if (NULL == L)
    {
        printf("删除失败\n");
        return;
    }

    while (L->next == L)
    {
        list_delete_head(L);
    }

    free(L);
    L = NULL;

    printf("删除成功\n");
    return;
}

// 任意位置删除
int list_delete_pos(NodePtr L, int pos)
{
    if (NULL == L || pos > L->len + 1 || pos < 1)
    {
        printf("删除失败\n");
        return -1;
    }

    NodePtr q = list_search_pos(L, pos - 1);

    NodePtr p = q->next;
    q->next = p->next;
    p->next->prio = q;
    free(p);
    p = NULL;
    // NodePtr p = L->next;
    // L->next = p->next;
    // p->next->prio = L;
    // free(p);
    // p = NULL;

    L->len--;
    printf("按位置删除成功\n");

    return 0;
}

//按位置修改
int list_change_pos(NodePtr L,int pos,datatype e)
{
    if (NULL == L || pos > L->len + 1 || pos < 1)
    {
        printf("修改失败\n");
        return -1;
    }

    NodePtr q = list_search_pos(L, pos);

    q->data = e;

    printf("按位置修改成功\n");

    return 0;
}

#include "00.h"

int main(int argc, char const *argv[])
{
    NodePtr L = list_create();
    if (NULL == L )
    {
        return -1;
    }

    putchar(10);

    list_insert_head(L,'H');
    list_insert_head(L,'e');
    list_insert_head(L,'l');
    list_insert_head(L,'l');
    list_insert_head(L,'o');
    list_show(L);
    putchar(10);

    list_insert_tail(L,'Z');
    list_show(L);
    putchar(10);

    list_delete_head(L);
    list_show(L);
    putchar(10);

    list_delete_pos(L,3);
    list_show(L);
    putchar(10);

    list_change_pos(L,4,'A');
    list_show(L);
    putchar(10);

    list_destroy(L);
    list_show(L);
    putchar(10);

    return 0;
}

实现结果

相关推荐
秋夫人33 分钟前
B+树(B+TREE)索引
数据结构·算法
李小星同志36 分钟前
高级算法设计与分析 学习笔记6 B树
笔记·学习
霜晨月c1 小时前
MFC 使用细节
笔记·学习·mfc
小江湖19941 小时前
元数据保护者,Caesium压缩不丢重要信息
运维·学习·软件需求·改行学it
代码雕刻家1 小时前
数据结构-3.1.栈的基本概念
c语言·开发语言·数据结构
AlexMercer10121 小时前
【C++】二、数据类型 (同C)
c语言·开发语言·数据结构·c++·笔记·算法
dot.Net安全矩阵1 小时前
.NET内网实战:通过命令行解密Web.config
前端·学习·安全·web安全·矩阵·.net
微刻时光2 小时前
Redis集群知识及实战
数据库·redis·笔记·学习·程序人生·缓存
^^为欢几何^^3 小时前
lodash中_.difference如何过滤数组
javascript·数据结构·算法
潮汐退涨月冷风霜4 小时前
机器学习之非监督学习(四)K-means 聚类算法
学习·算法·机器学习