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

C语言编程--16.删除链表的倒数第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]

提示

链表中结点的数目为 sz
1 <= sz <= 30
0 <= Node.val <= 100
1 <= n <= sz

代码:

/*** Definition for singly-linked list.* struct ListNode {*     int val;*     struct ListNode *next;* };*/
// 函数用于从单链表的末尾删除第 n 个节点,并返回新的链表头指针
struct ListNode* removeNthFromEnd(struct ListNode* head, int n) {// 用于遍历链表的指针,初始指向链表头struct ListNode* node = head;// 用于记录链表节点的数量int count = 0;   // 遍历链表,统计节点数量while (node) {node = node->next;count++;}// 如果要删除的节点是头节点(即链表长度等于 n)if (count == n) {// 保存原头节点的下一个节点struct ListNode* temp = head->next;// 将头指针指向下一个节点,相当于删除了原头节点head = head->next;// 返回新的头节点return head;}// 将指针重新指向链表头,准备再次遍历node = head;// 计算要删除节点的前一个节点的位置int m = count - n;// 遍历到要删除节点的前一个节点for (int i = 0; i < m - 1; i++)node = node->next;// 保存要删除的节点struct ListNode* temp = node->next;// 将前一个节点的 next 指针指向要删除节点的下一个节点,跳过要删除的节点node->next = node->next->next;  // 返回原链表的头节点(链表已被修改)return head;
}

代码分析:

优点

  1. 逻辑清晰:代码采用了先遍历一次链表统计节点数量,再根据数量计算要删除节点的位置,最后进行删除操作的思路,整体逻辑比较直观,容易理解。
  2. 处理头节点情况:通过判断链表长度和 n 的关系,专门处理了要删除的节点是头节点的情况,保证了代码的正确性。

缺点

  1. 两次遍历链表:代码中先对链表进行了一次遍历统计节点数量,然后又进行了一次遍历找到要删除节点的前一个节点。这种方式增加了时间复杂度,使得时间复杂度为 O(n),在一些对时间要求较高的场景下可能效率较低。
  2. 未释放内存:在删除节点时,保存了要删除的节点指针 temp,但没有释放该节点占用的内存,会导致内存泄漏问题。
  3. 边界条件处理不够完善:代码仅处理了要删除的节点是头节点的情况,对于其他一些特殊情况(例如空链表等)没有进行额外的处理,健壮性不足。
  4. 没有使用虚拟头节点:使用虚拟头节点可以简化链表操作,特别是在处理头节点删除等情况时,可以避免一些特殊情况的判断,使代码更加简洁和统一。但此代码没有采用这种方式。

为了改进这些缺点,可以考虑使用双指针法(快慢指针),只遍历一次链表就能找到要删除的节点,同时注意释放内存和完善边界条件的处理。

http://www.xdnf.cn/news/1672.html

相关文章:

  • 触觉智能RK3506核心板,工业应用之RK3506 RT-Linux实时性测试
  • arm64适配系列文章-第九章-arm64环境上sentinel的部署
  • 【mysql】windows mysql命令
  • Verilog 语法 (一)
  • springboot在eclipse里面运行 run as 是Java Application还是 Maven
  • Java面试场景篇:分布式锁的实现与组件详解
  • MCP‌和LangGraph‌结合2
  • 基于Vue3 的 h5监听从左到右手滑返回上一页
  • 开源模型应用落地-语音合成-MegaTTS3-零样本克隆与多语言生成的突破
  • 从工作到娱乐:Codigger Desktop 让桌面环境更智能
  • c#-命名和书写规范
  • k8s基于角色的访问控制(RBAC)
  • GPT-4o最新图像生成完全指南:10大应用场景与提示词模板
  • opencv--图像变换
  • 悟空统计:小而美的网站流量统计工具,免费好用
  • 【金仓数据库征文】从云计算到区块链:金仓数据库的颠覆性创新之路
  • ThreadLocal
  • 医学图像(DICOM数据)读取及显示(横断面、冠状面、矢状面、3D显示)为什么用ITK+VTK,单独用ITK或者VTK能实一样功能吗?
  • centos离线安装ssh
  • C语言中封装JSON数组对象
  • 深度解析@SneakyThrows注解:原理、应用与最佳实践
  • 23种设计模式-行为型模式之策略模式(Java版本)
  • 基于 EFISH-SBC-RK3588 的无人机环境感知与数据采集方案
  • DPIN在AI+DePIN孟买峰会阐述全球GPU生态系统的战略愿景
  • MySQL:数据库设计
  • 【C++入门:类和对象】[3]
  • LJF-Framework 第15章 想想搞点啥-若依管理系统兼容一下
  • 在Windows11上用wsl配置docker register 镜像地址
  • django admin 添加自定义页面
  • 从码云上拉取项目并在idea配置npm时完整步骤