当前位置: 首页 > news >正文

【练习】【链表】力扣热题100 19. 删除链表的倒数第 N 个结点

题目

  1. 删除链表的倒数第 N 个结点

给你一个链表,删除链表的倒数第 n 个结点,并且返回链表的头结点。

示例 1:

输入:head = [1,2,3,4,5], n = 2

输出:[1,2,3,5]

示例 2:

输入:head = [1], n = 1

输出:[]

示例 3:

输入:head = [1,2], n = 1

输出:[1]

来源:力扣热题100 19. 删除链表的倒数第 N 个结点


思路(注意事项)

三个指针。
pre:删除节点的前置指针
p:删除节点
q :距离指针

  • 但也可以简化为两个指针,另外需要在输入的链表上加上头节点。 (详见ds简化版)

纯代码

class Solution {
public:
    ListNode* removeNthFromEnd(ListNode* head, int n) {
        int sum = 0;
        ListNode *t = head;
        while (t != nullptr) sum ++, t = t ->next;
        if (n == sum) return head -> next;

        if (head == nullptr || head -> next == nullptr) return nullptr;
        ListNode *pre = head, *p = pre -> next, *q = p;

        while (n --) q = q -> next;

        while (q != nullptr)
        {
            q = q -> next;
            p = p -> next;
            pre = pre -> next;
        }

        pre -> next = p -> next;
        return head;
    }
};

题解(加注释)

class Solution {
public:
    ListNode* removeNthFromEnd(ListNode* head, int n) {
        // 计算链表的长度
        int length = 0;
        ListNode* t = head;
        while (t != nullptr) {
            length++;
            t = t->next;
        }

        // 如果删除的是头节点,直接返回头节点的下一个节点
        if (n == length) {
            return head->next;
        }

        // 如果链表为空或只有一个节点,返回空链表
        if (head == nullptr || head->next == nullptr) {
            return nullptr;
        }

        // 初始化指针
        ListNode* pre = head; // 指向要删除节点的前一个节点
        ListNode* p = pre->next; // 指向要删除的节点
        ListNode* q = p; // 用于遍历的指针

        // 将 q 移动到第 n 个节点
        while (n--) {
            q = q->next;
        }

        // 移动 pre、p 和 q,直到 q 到达链表末尾
        while (q != nullptr) {
            q = q->next;
            p = p->next;
            pre = pre->next;
        }

        // 删除节点
        pre->next = p->next;

        return head;
    }
};

(详见ds简化版)

题解(ds简化)

class Solution {
public:
    ListNode* removeNthFromEnd(ListNode* head, int n) {
        ListNode* L = new ListNode(0); // 创建虚拟头节点
        L->next = head;
        ListNode* fast = L;
        ListNode* slow = L;

        // 快指针先移动 n 步
        for (int i = 0; i <= n; i++) fast = fast->next;

        // 同时移动快慢指针,直到快指针到达链表末尾
        while (fast != nullptr) {
            fast = fast->next;
            slow = slow->next;
        }

        // 删除节点
        slow->next = slow->next->next;

        return L->next; // 返回结果链表的头节点
    }
};

相关文章:

  • 扩散语言模型:从图像生成到文本创造的范式跃迁
  • redis事务详解
  • 【FastGPT】如何新增用户修改密码
  • [经验总结]Exec format error——Shebang解释器声明省略的锅
  • 非平衡数据的处理
  • 计算机网络——子网掩码
  • CF1363C Game On Leaves【题解】
  • 使用Nokov度量运动捕捉系统进行定位
  • Elasticsearch --- 相关基础知识整理
  • 【FAQ】HarmonyOS SDK 闭源开放能力 —Map Kit(5)
  • HTML前端手册
  • AI编程,常见的AI编程工具有哪些?如何用AI编程做一个简单的小软件?
  • Axure高保真Element框架元件库
  • 无线通信中 RSRP、RSRQ、RSSI、SINR
  • 【Hudi-SQL DDL创建表语法】
  • 多视图几何--1关于变换-1.0写在前面的话
  • 【多模态目标检测】【AAAI 2025】FD2-Net
  • DeepSeek 助力 Vue3 开发:打造丝滑的表格(Table)示例1:基础表格
  • kotlin高级用法总结
  • ArcGIS Pro 经纬网添加全解析:从布局到样式优化
  • 郑州网站建设市场/永久观看不收费的直播
  • 网站建设年费/韩国日本比分
  • 移动互联网的应用举例/手机流畅优化软件
  • 计算机专业设计一个网站/推广工作的流程及内容
  • 怎么建立自己的个人网站/什么是网络营销策略
  • 想找做拼接屏的公司去哪个网站/百度识图在线识别