当前位置:首页 > 其他 > 手把手教你理解单向链表:代码注释+新手入门指南

手把手教你理解单向链表:代码注释+新手入门指南

4周前 (06-19)

一、简介和应用

单向链表是一种基础的数据结构,它由一系列节点组成,每个节点包含数据和指向下一个节点的指针。这种结构在数据存储和动态操作中非常实用,例如实现队列,或在需要频繁插入、删除的场景中(如用户登录记录、任务列表等)。相比数组链表无需连续内存空间,插入和删除效率更高,但无法随机访问元素。

二、特点和注意事项

特点:

    1. 灵活性:节点动态分配,支持任意长度。

    2. 简单性:单向指针,逻辑清晰,适合新手入门。

    3. 操作高效:插入和删除节点只需修改指针,时间复杂度为O(1)(找到位置后)。

注意事项:

    1.避免空指针操作:访问节点前需判断是否为nullptr。

    2.内存管理:手动分配节点(如new node)后,需确保程序结束前释放(未实现删除功能时需注意)。

    3.索引越界:插入、删除等操作需检查索引是否合法。

三、代码的实现步骤

1. 定义节点结构:包含数据data和指向下一个节点的指针next。

2. 创建链表类:linklist类以head指针指向链表头部。

3. 添加节点:从头部遍历到末尾,将新节点插入末尾。

4. 插入节点:根据索引找到目标位置的前一个节点,插入新节点并调整指针。

5. 删除节点:找到目标位置前一个节点,跳过要删除的节点并连接后续节点。

6. 修改和查询:通过索引遍历到目标节点,修改数据或返回数据。

7. 反转链表:提供递归和非递归两种方法,改变指针方向形成逆序链表。

四、代码与注释

#include <iostream>
using namespace std;

// 定义节点结构
struct node {
    int data = 0;          // 节点存储的数据(默认值0)
    node* next = nullptr;  // 指向下一个节点的指针
};

class linklist {
public:
    node* head = new node;  // 链表头部节点(初始化为空节点)

    // 1. 添加节点到末尾
    void add(int data) {
        node* tmp = head;   // 临时指针从头部开始遍历
        while (tmp->next!= nullptr) {  // 循环直到末尾
            tmp = tmp->next;
        }
        node* datanode = new node;  // 创建新节点
        datanode->data = data;     // 赋值数据
        tmp->next = datanode;      // 将末尾指针指向新节点
    }

    // 2. 在指定索引插入节点
    void insert(int data, int idx) {
        node* datanode = new node;  // 创建新节点
        datanode->data = data;
        node* tmp = head;           // 临时指针从头部开始
        for (int i = 0; i < idx; i++) {  // 循环到索引位置的前一个节点
            tmp = tmp->next;
        }
        datanode->next = tmp->next;  // 新节点指向原索引位置的节点
        tmp->next = datanode;        // 前一个节点指向新节点
    }

    // 3. 删除指定索引的节点
    void deleteNode(int idx) {
        node* tmp = head;
        for (int i = 0; i < idx; i++) {
            tmp = tmp->next;
        }
        tmp->next = tmp->next->next;  // 跳过要删除的节点,连接后续节点
    }

    // 4. 修改指定索引节点的数据
    void change(int data, int idx) {
        node* tmp = head;
        for (int i = 0; i <= idx; i++) {  // 注意:i <= idx,因为要访问到目标节点
            tmp = tmp->next;
        }
        tmp->data = data;
    }

    // 5. 查询指定索引的节点数据
    int select(int idx) {
        node* tmp = head;
        for (int i = 0; i <= idx; i++) {
            tmp = tmp->next;
        }
        return tmp->data;  // 返回目标节点的数据
    }

    // 6. 反转链表(递归方法)
    node* reverse(node* head) {
        if (head == nullptr || head->next == nullptr) {  // 递归终止条件:空链表或只有一个节点
            return head;
        }
        node* newHead = reverse(head->next);            // 递归处理后续节点
        head->next->next = head;                       // 原头部的下一个节点指向原头部
        head->next = nullptr;                          // 原头部指向空(新链表的末尾)
        linklist::head->next = newHead;                // 更新链表头部指针(注意:此处可能影响原链表结构,需谨慎使用)
        return newHead;
    }

    // 7. 反转链表(迭代方法)
    node* otherReverse(node* head) {
        node* a = head;      // 当前节点
        node* b = a->next;   // 下一个节点
        a->next = nullptr;   // 初始化反转后的头部
        while (b) {          // 迭代反转
            node* tmp = b->next;     // 暂存下一个节点
            b->next = a;             // 反转指针方向
            a = b;                   // 更新当前节点
            b = tmp;                 // 更新下一个节点
        }
        linklist::head->next = a;     // 更新链表头部指针
        return a;
    }
};

五、总结

单向链表是数据结构的入门基石,掌握其原理和操作能帮助你理解更复杂的链表(如双向链表、循环链表)。本文通过代码注释和步骤拆解,带你从零开始构建链表,并实现基本操作及反转。建议新手多动手实践,尝试修改代码(如添加删除节点的内存释放功能),逐步加深理解。记住:指针操作需谨慎,逻辑清晰是关键!


单向链表

原创内容 转载请注明出处

分享给朋友:

相关文章

力扣501题最优解:不用额外空间找出BST中的众数?这个解法让你大开眼界

力扣501题最优解:不用额外空间找出BST中的众数?这个解法让你大开眼界

题目解读‌:在二叉搜索树的世界里,每个节点都默默记录着自己的数值。现在我们需要找出这些数值中出现频率最高的那些数字,也就是所谓的"众数"。有趣的是,二叉搜索树本身具有左小右大的特性...

手把手教你实现哈希表:从代码到原理的新手友好指南

一、简介和应用哈希表(Hash Table)是一种高效的数据结构,通过哈希函数将键(Key)映射到存储位置,实现O(1)时间复杂度的查找、插入和删除操作。它广泛应用于缓存系统、数据库索引、字典查询等场...

【牛客157题】:反转链表指定区间(虚拟头节点解法)

【牛客157题】:反转链表指定区间(虚拟头节点解法)

一、题目解读牛客第157题要求反转链表中第m到n个节点(包含m和n)的区间,并保持其他节点顺序不变。例如,给定链表1→2→3→4→5,m=2,n=4,应返回1→4→3→2→5。题目重点在于处理边界条件...

手搓顺序表实现栈 代码详解及新手教程——从原理到实现的完整指南

一、简介和特点顺序栈是一种基于数组实现的后进先出(LIFO)数据结构。通过动态数组管理存储空间,它具备以下特点:1. 数组存储:数据连续存储,支持随机访问,访问效率高。2. 动态扩容:当栈满时自动扩展...

发表评论

访客

看不清,换一张

◎欢迎参与讨论,请在这里发表您的看法和观点。