LeetCode 热题 Hot100

目录


已练习
46. 全排列
55. 跳跃游戏
70. 爬楼梯
62. 不同路径
64. 最小路径和
78. 子集
79. 单词搜索
98. 验证二叉搜索树
32. 最长有效括号
146. LRU 缓存机制
198. 打家劫舍
221. 最大正方形
239. 滑动窗口最大值
279. 完全平方数
300. 最长递增子序列
309. 最佳买卖股票时机含冷冻期
337. 打家劫舍 III
322. 零钱兑换

46. 全排列

题目描述

给定一个 没有重复 数字的序列,返回其所有可能的全排列。

示例:

输入: [1,2,3]

输出:

[

[1,2,3],

[1,3,2],

[2,1,3],

[2,3,1],

[3,1,2],

[3,2,1]

]

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/permutations
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

思路

这里注意res.add 要重新new一个ArrayList,不然list改变的话会改变res里面的值。

class Solution {
   
    public List<List<Integer>> permute(int[] nums) {
   
        List<List<Integer>> res = new ArrayList<>();
        int len = nums.length;
        if(len == 0)
            return res;
        ArrayList<Integer> list = new ArrayList<>();
        for(int i = 0;i < nums.length;++i){
   
            list.add(nums[i]);
        }
        helpPermute(len,res,list,0);
        return res;
    }

    public void helpPermute(int len,List<List<Integer>> res,ArrayList<Integer> list,int first){
   
        if(first == len){
   
            res.add(new ArrayList<Integer>(list));
        }
        for(int i = first;i < len;++i){
   
            Collections.swap(list,first,i);
            helpPermute(len,res,list,first+1);
            Collections.swap(list,first,i);
        }
    }
}

55. 跳跃游戏

题目描述

给定一个非负整数数组 nums ,你最初位于数组的 第一个下标 。

数组中的每个元素代表你在该位置可以跳跃的最大长度。

判断你是否能够到达最后一个下标。

示例 1:

输入:nums = [2,3,1,1,4]

输出:true

解释:可以先跳 1 步,从下标 0 到达下标 1, 然后再从下标 1 跳 3 步到达最后一个下标。

示例 2:

输入:nums = [3,2,1,0,4]

输出:false

解释:无论怎样,总会到达下标为 3 的位置。但该下标的最大跳跃长度是 0 , 所以永远不可能到达最后一个下标。

提示:

  • 1 <= nums.length <= 3 * 104
  • 0 <= nums[i] <= 105

思路

挨个跳,保存能跳的最远的坐标lastIndex,比较当前坐标和最远坐标。

class Solution {
   
    public boolean canJump(int[] nums) {
   
        int lastIndex = 0;
        for(int i = 0;i < nums.length;++i){
   
            if(i > lastIndex)
                return false;
            lastIndex = Math.max(lastIndex,i+nums[i]);
        }
        return true;
    }
}

70. 爬楼梯

题目描述

假设你正在爬楼梯。需要 n 阶你才能到达楼顶。

每次你可以爬 1 或 2 个台阶。你有多少种不同的方法可以爬到楼顶呢?

注意:给定 n 是一个正整数。

示例 1:

输入: 2

输出: 2

解释: 有两种方法可以爬到楼顶。

  1. 1 阶 + 1 阶

  2. 2 阶

示例 2:

输入: 3

输出: 3

解释: 有三种方法可以爬到楼顶。

  1. 1 阶 + 1 阶 + 1 阶

  2. 1 阶 + 2 阶

  3. 2 阶 + 1 阶

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/climbing-stairs
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

思路

f(i) = f(i-1)+f(i-2)

class Solution {
   
    public int climbStairs(int n) {
   
        int p = 0,q = 0,r = 1;
        for(int i = 0;i < n;++i){
   
            p = q;
            q = r;
            r = p+q;
        }
        return r;
    }
}

62. 不同路径

题目描述

一个机器人位于一个 m x n 网格的左上角 (起始点在下图中标记为 “Start” )。

机器人每次只能向下或者向右移动一步。机器人试图达到网格的右下角(在下图中标记为 “Finish” )。

问总共有多少条不同的路径?

示例 1:
在这里插入图片描述

输入:m = 3, n = 7

输出:28

示例 2:

输入:m = 3, n = 2

输出:3

解释:

从左上角开始,总共有 3 条路径可以到达右下角。

  1. 向右 -> 向下 -> 向下

  2. 向下 -> 向下 -> 向右

  3. 向下 -> 向右 -> 向下

示例 3:

输入:m = 7, n = 3

输出:28

示例 4:

输入:m = 3, n = 3

输出:6

提示:

  • 1 <= m, n <= 100
  • 题目数据保证答案小于等于 2 * 109

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/unique-paths
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

思路

class Solution {
   
    public int uniquePaths(int m, int n) {
   
        int[][] dp = new int[m][n];
        for(int i = 0;i < m;++i){
   
            dp[i][0] = 1;
        }
        for(int i = 0;i < n;++i){
   
            dp[0][i] = 1;
        }
        for(int i = 1;i < m;++i){
   
            for(int j = 1;j < n;++j){
   
                dp[i][j] = dp[i-1][j] + dp[i][j-1];
            }
        }
        return dp[m-1][n-1];
    }
}

64. 最小路径和

题目描述

给定一个包含非负整数的 m x n 网格 grid ,请找出一条从左上角到右下角的路径,使得路径上的数字总和为最小。

说明:每次只能向下或者向右移动一步。

示例 1:
在这里插入图片描述

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

输出:7

解释:因为路径 1→3→1→1→1 的总和最小。

示例 2:

输入:grid = [[1,2,3],[4,5,6]]

输出:12

提示:

  • m == grid.length
  • n == grid[i].length
  • 1 <= m, n <= 200
  • 0 <= grid[i][j] <= 100

来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/minimum-path-sum
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。

思路

class Solution {
   
    public int minPathSum(int[][] grid) {
   
        int rows = grid.length,cols = grid[0].length;
        int[][] dp = new int[rows][cols];
        dp[0][0] = grid[0][0];
        for(int i = 1;i < rows;++i){
   
            dp[i][0] = dp[i-1][0] + grid[i][0];
        }
        for(int i = 1;i < cols;++i){
   
            dp[0][i] = dp[0][i-1] + grid[0][i];
        }
        for(int i = 1;i < rows;i++){
   
            for(int j = 1;j < cols;j++){
   
                dp[i][j] = Math.min(dp[i-1][j]
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值