实现双向链表的增删改查

头文件

复制代码
#pragma once
#define _CRT_SECURE_NO_WARNINGS 1
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
typedef int LTDataType;
typedef struct ListNode {
    LTDataType data;
    struct ListNode* prev;
    struct ListNode* next;
} LTNode;
//void LTInit(LTNode** pphead);
// 初始化双向链表,返回头结点指针
LTNode* LTInit();
// 销毁双向链表,释放所有节点
void LTDestroy(LTNode* phead);
// 打印双向链表
void LTPrint(LTNode* phead);
// 判断链表是否为空
bool LTEmpty(LTNode* phead);
// 尾插
void LTPushBack(LTNode* phead, LTDataType x);
// 尾删
void LTPopBack(LTNode* phead);
// 头插
void LTPushFront(LTNode* phead, LTDataType x);
// 头删
void LTPopFront(LTNode* phead);
//在pos位置之后插入数据
void LTInsert(LTNode* pos, LTDataType x);
// 删除 pos 位置的节点
void LTErase(LTNode* pos);
// 查找数据 x,返回对应节点的指针
LTNode* LTFind(LTNode* phead, LTDataType x);

函数实现

复制代码
#define _CRT_SECURE_NO_WARNINGS 1
#include "s.h"
// 初始化双向链表,返回头结点指针
LTNode* LTInit() {
    LTNode* head = (LTNode*)malloc(sizeof(LTNode));
    if (head == NULL) {
        perror("malloc failed");
        exit(-1);
    }
    head->next = head;
    head->prev = head;
    return head;
}

// 销毁双向链表,释放所有节点
void LTDestroy(LTNode* phead) {
    LTNode* cur = phead->next;
    while (cur != phead) {
        LTNode* next = cur->next;
        free(cur);
        cur = next;
    }
    free(phead);
}

// 打印双向链表
void LTPrint(LTNode* phead) {
    LTNode* cur = phead->next;
    while (cur != phead) {
        printf("%d -> ", cur->data);
        cur = cur->next;
    }
    printf("NULL\n");
}

// 判断链表是否为空
bool LTEmpty(LTNode* phead) {
    return phead->next == phead;
}

// 尾插
void LTPushBack(LTNode* phead, LTDataType x) {
    LTNode* new_node = (LTNode*)malloc(sizeof(LTNode));
    new_node->data = x;

    // 插入到尾部
    new_node->prev = phead->prev;
    new_node->next = phead;
    phead->prev->next = new_node;
    phead->prev = new_node;
}

// 尾删
void LTPopBack(LTNode* phead) {
    if (LTEmpty(phead)) return;
    LTNode* tail = phead->prev;
    tail->prev->next = phead;
    phead->prev = tail->prev;
    free(tail);
}

// 头插
void LTPushFront(LTNode* phead, LTDataType x) {
    LTNode* new_node = (LTNode*)malloc(sizeof(LTNode));
    new_node->data = x;

    // 插入到头部
    new_node->next = phead->next;
    new_node->prev = phead;
    phead->next->prev = new_node;
    phead->next = new_node;
}

// 头删
void LTPopFront(LTNode* phead) {
    if (LTEmpty(phead)) return;

    LTNode* first = phead->next;
    phead->next = first->next;
    first->next->prev = phead;
    free(first);
}

// 在 pos 位置之后插入数据
void LTInsert(LTNode* pos, LTDataType x) {
    LTNode* new_node = (LTNode*)malloc(sizeof(LTNode));
    new_node->data = x;

    new_node->next = pos->next;
    new_node->prev = pos;
    pos->next->prev = new_node;
    pos->next = new_node;
}

// 删除 pos 位置的节点
void LTErase(LTNode* pos) {
    pos->prev->next = pos->next;
    pos->next->prev = pos->prev;
    free(pos);
}

// 查找数据 x,返回对应节点的指针
LTNode* LTFind(LTNode* phead, LTDataType x) {
    LTNode* cur = phead->next;
    while (cur != phead) {
        if (cur->data == x) {
            return cur;
        }
        cur = cur->next;
    }
    return NULL;
}

测试文件

复制代码
#define _CRT_SECURE_NO_WARNINGS 1
#include "s.h"
int main() {
    LTNode* list = LTInit();

    LTPushBack(list, 10);
    LTPushBack(list, 20);
    LTPushBack(list, 30);

    LTPrint(list);

    LTNode* pos = LTFind(list, 20);
    if (pos) {
        LTInsert(pos, 25);
    }
    LTPrint(list);

    LTPopBack(list);
    LTPrint(list);

    LTDestroy(list);
    return 0;
}

实现效果

相关推荐
Fanxt_Ja13 小时前
【LeetCode】算法详解#15 ---环形链表II
数据结构·算法·leetcode·链表
侃侃_天下13 小时前
最终的信号类
开发语言·c++·算法
茉莉玫瑰花茶14 小时前
算法 --- 字符串
算法
博笙困了14 小时前
AcWing学习——差分
c++·算法
NAGNIP14 小时前
认识 Unsloth 框架:大模型高效微调的利器
算法
NAGNIP14 小时前
大模型微调框架之LLaMA Factory
算法
echoarts14 小时前
Rayon Rust中的数据并行库入门教程
开发语言·其他·算法·rust
Python技术极客14 小时前
一款超好用的 Python 交互式可视化工具,强烈推荐~
算法
徐小夕14 小时前
花了一天时间,开源了一套精美且支持复杂操作的表格编辑器tablejs
前端·算法·github
小刘鸭地下城14 小时前
深入浅出链表:从基础概念到核心操作全面解析
算法