算法入门线性枚举(中等 - 第一题)LeetCode 19

Posted 英雄哪里出来

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了算法入门线性枚举(中等 - 第一题)LeetCode 19相关的知识,希望对你有一定的参考价值。

🙉饭不食,水不饮,题必须刷🙉

还不会C语言,和我一起打卡!
🌞《光天化日学C语言》🌞

LeetCode 太难?上简单题!
🧡《C语言入门100例》🧡

LeetCode 太简单?大神盘他!
🌌《夜深人静写算法》🌌

一、题目

1、题目描述

  给你一个链表,删除链表的倒数第 n n n 个结点,并且返回链表的头结点。
  样例: h e a d = [ 1 , 2 , 3 , 4 , 5 , 6 ] head = [1,2,3,4,5,6] head=[1,2,3,4,5,6] n = 5 n = 5 n=5 输出 [ 1 , 3 , 4 , 5 , 6 ] [1,3,4,5,6] [1,3,4,5,6]

2、基础框架

  • c++ 版本给出的基础框架代码如下:
/**
 * Definition for singly-linked list.
 * 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) {
    }
};
  • 这里引入了一种数据结构 链表 ListNode
  • 成员有两个:数据域val和指针域next
  • 返回的是链表的某个结点;

3、原题链接

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

二、解题报告

1、思路分析

  • 我们可以通过一个 O ( n ) O(n) O(n) 的枚举,将所有的链表节点按照顺序放进一个数组中,于是,对于一个长度为 L L L 的链表。

我们采用数学归纳法:
  如果删除的是倒数第 1 1 1 个,则删除数组的第 L − 1 L-1 L1 个元素,再把原数组组织成链表;
  如果删除的是倒数第 2 2 2 个,则删除数组的第 L − 2 L-2 L2 个元素,再把原数组组织成链表;
  如果删除的是倒数第 3 3 3 个,则删除数组的第 L − 3 L-3 L3 个元素,再把原数组组织成链表;
  …
  如果删除的是倒数第 L L L 个,则删除数组的第 0 个链表节点,再把原数组组织成链表;

  • 所以我们可以先做一次遍历,重新组织一个新的链表,并且将第 L − n L - n Ln 忽略;再返回链表头结点即可。

2、时间复杂度

  • 线性枚举为 O ( n ) O(n) O(n)

3、代码详解

class Solution {
public:
    ListNode* removeNthFromEnd(ListNode* head, int n) {
        vector <ListNode*> nodes;
        ListNode *now = head;
        while(now) {
            nodes.push_back(now);                     // (1)
            now = now->next;
        }
        if(n == nodes.size()) {
            head = head->next;                        // (2)
        }else {
            ListNode *last = head;
            for(int i = 1; i < nodes.size(); ++i) {
                if(i == nodes.size() - n) {
                    continue;                         // (3)
                }
                last->next = nodes[i];                // (4)
                last = nodes[i];
            }
            last->next = NULL;
        }
        return head;
    }
};
  • ( 1 ) (1) (1) 通过一个 O ( n ) O(n) O(n) 的枚举,将所有的链表节点按照顺序放进一个数组中;
  • ( 2 ) (2) (2) 当删除倒数最后一个元素时,直接将根节点指向它的next即可;
  • ( 3 ) (3) (3) 需要删除的节点,不再组织到链表中;
  • ( 4 ) (4) (4) last代表当前链表最后一个元素;

三、本题小知识

链表问题如果在时间复杂度允许的情况下,是可以用数组来代替的;


以上是关于算法入门线性枚举(中等 - 第一题)LeetCode 19的主要内容,如果未能解决你的问题,请参考以下文章

⭐算法入门⭐《线性枚举》中等03 —— LeetCode 27. 移除元素

⭐算法入门⭐《线性枚举》中等02 —— LeetCode 628. 三个数的最大乘积

算法入门 04模拟(中等 - 第一题)LeetCode 8

算法入门双指针(中等 - 第一题)LeetCode 3

算法入门同余(中等 - 第一题)LeetCode 189

算法入门广度优先搜索(中等 - 第一题)LeetCode 994