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

算法每日一练 (4)

💢欢迎来到张胤尘的技术站
💥技术如江河,汇聚众志成。代码似星辰,照亮行征程。开源精神长,传承永不忘。携手共前行,未来更辉煌💥

文章目录

  • 算法每日一练 (4)
    • 删除链表的倒数第 N 个节点
      • 题目描述
      • 解题思路
      • 解题代码
        • `c/c++`
        • `golang`
        • `lua`

官方站点: 力扣 Leetcode

算法每日一练 (4)

删除链表的倒数第 N 个节点

题目地址:删除链表的倒数第 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

进阶: 你能尝试使用一趟扫描实现吗?

解题思路

  • 首先处理边界条件,由题意可知被删除节点的次序值是小于或等于链表节点总数,并且大于等于1的,那么一定当整个链表只有一个节点时,被删除的节点次序值一定是1,故结果值一定是空(nilnullptr 或者 NULL)。
  • 另外由进阶要求得知仅仅使用一趟遍历完成题目,因为需要保证链表中节点的相对顺序,而且只能通过指针移动删除指定节点(因为只能一次遍历),因为数组(动态数组)本身根据链表的遍历后存储是有序的,而且可以通过下标直接操作链表节点,那么可以直接选择数组作为辅助。
  • 创建辅助数组(动态数组),同时也需要创建一个整形变量用于计算链表中的节点总数,后续可以直接通过总数值和待删除元素的次序值计算后得出待删除元素在数组(动态数组)的下标值。如下图所示:
    在这里插入图片描述
  • 通过临时指针变量 t 循环的将链表中的节点添加到数组(动态数组)中,并同时在循环中计算链表中节点总数。
  • 紧接着,只剩下两种情况需要判断:
    • 如果待删除的节点的次序值和节点的总数值相等,那么待删除节点就是头节点,直接将头节点指针 head 指向数组中第二个节点即可,不需要再进行下标计算。
    • 另外一种情况就是非头节点,那么需要根据上述公式计算出待删除节点在数组中的下标值后,将(下标值 - 1)的下个节点指向(下标值)的下个节点即可(进行指针移动删除中间元素)。
  • 最后返回 head 头指针即可。

解题代码

c/c++
#include <vector>

struct ListNode
{
    int val;
    ListNode *next;
    ListNode() : val(0), next(nullptr) {}
    ListNode(int x) : val(x), next(nullptr) {}
    ListNode(int x, ListNode *next) : val(x), next(next) {}
};

class Solution
{
public:
    ListNode *removeNthFromEnd(ListNode *head, int n)
    {
        if (!head->next)
            return nullptr;

        std::vector<ListNode *> vec;
        ListNode *t = head;

        while (t)
        {
            vec.push_back(t);
            t = t->next;
        }
        
		int cnt = vec.size();
        if (n == cnt)
            head = vec[1];
        else
        {
            int target = cnt - n;
            vec[target - 1]->next = vec[target]->next;
        }

        return head;
    }
};
golang
type ListNode struct {
	Val  int
	Next *ListNode
}

func removeNthFromEnd(head *ListNode, n int) *ListNode {
	if head.Next == nil {
		return nil
	}

	slice := make([]*ListNode, 0)
	t := head

	for t != nil {
		slice = append(slice, t)
		t = t.Next
	}
	
	count := len(slice)
	if n == count {
		head = slice[1]
	} else {
		target := count - n
		slice[target-1].Next = slice[target].Next
	}

	return head
}
lua
local ListNode = {}

function ListNode:new(val, next)
    local obj = {}
    setmetatable(obj, self)
    self.__index = self
    obj.Val = val or 0
    obj.Next = next or nil
    return obj
end

local function removeNthFromEnd(head, n)
    if head.Next == nil then
        return nil
    end

    local arr = {}
    local t = head

    while t ~= nil do
        table.insert(arr, t)
        t = t.Next
    end
	
	local count = #arr
    if n == count then
        head = arr[2]
    else
        local target = count - n + 1
        arr[target - 1].Next = arr[target].Next
    end

    return head
end

🌺🌺🌺撒花!

如果本文对你有帮助,就点关注或者留个👍
如果您有任何技术问题或者需要更多其他的内容,请随时向我提问。

在这里插入图片描述

相关文章:

  • 【Winform】深入理解C#中的异常处理:以WinForms应用程序为例
  • GB28181协议下的RTP传输
  • Android Loader机制解析
  • MapReduce 读取 Hive ORC ArrayIndexOutOfBoundsException: 1024 异常解决
  • Excell 代码处理
  • kafka基本知识
  • Prompt Engineering的重要性
  • JAVAweb-JS基本数据类型,变量,DOM,pop,push函数,事件
  • 【Python爬虫(47)】探秘分布式爬虫性能:从测试到优化之路
  • 哈希表入门到精通:从原理到 Python 实现全解析
  • 洛谷P9242 [蓝桥杯 2023 省 B] 接龙数列
  • 【SpringBoot教程】SpringBoot整合Caffeine本地缓存及Spring Cache注解的使用
  • SSI用量子计算来玩AI
  • 策略模式Spring框架下开发实例
  • AI(14)-prompt
  • 跟据spring boot版本,查看对应的tomcat,并查看可支持的tomcat的版本范围
  • Windows11安装GPU版本Pytorch2.6教程
  • [Android]文本多的时候让TextView的字体自动变小
  • 量子比特的实现与优化技术:解密量子计算的核心
  • 【Python爬虫(45)】Python爬虫新境界:分布式与大数据框架的融合之旅
  • 政府网站排版布局/沈阳百度快照优化公司
  • 做网站建设有前途那/长沙网站提升排名
  • 石家庄网站模板建站/百度投诉电话
  • 浙江省建设工程质量协会网站/腾讯云建站
  • 设计师 推荐 网站/网站宣传方法
  • 番禺网站制作设计/自建站怎么推广