手撕代码题型总结

1. 类型题

类型题Ⅰ:单调栈
类型题Ⅱ:位运算
类型题Ⅲ:双指针及哈希表求和
类型题Ⅳ:前缀和
类型题Ⅴ:回溯法

2. 动态规划

动态规划Ⅰ:斐波那契数列
动态规划Ⅱ:矩阵路径
动态规划Ⅲ:数组区间
动态规划Ⅳ:分割整数


【动态规划解题思路】

  • 明确状态:这个状态实际就是在求解过程中的变量,即我们要求的目标
  • dp 数组定义:dp 数组一般用于存放每个状态位的状态
  • 明确选择
  • 寻找状态之间的关系:找状态转移方程,这一步是关键
  • 确定 base case:即初始化 dp 数组,找到最简单、能一眼看出来的初始状态

如何找动态规划和状态转移间的关系? 通用技巧:数学归纳法

  • 明确 dp 数组所存数据的含义,想要表示什么,决定了后面的状态转移公式;
  • 根据 dp 数组的定义,运用数学归纳法的思想,假设 dp[0...i-1] 都已知,想办法求出 dp[i]
  • 如果感觉无法归纳出状态转移关系,可能是 dp 数组定义不恰当,也可能是 dp 数组存储的信息不够,考虑将其扩展到二维数组甚至三维数组;
  • 另外,动规问题很多都会有 dp 数组第 i 个位置的状态会和前 i-1 个状态都有某些关联,此时就需要用到二重循环,外层循环遍历 dp 数组,内层循环用于求解每个位置的状态。

【动态规划和贪心算法】

动态规划和贪心算法都是用来求 “最优化问题”,且都必须有 “最优子结构”(一个问题的最优解包含其子问题的最优解)。贪心可以解决的问题,动态规划都能解决,可以说,贪心是动态规划的一个特例。

  • 动态规划:自底向上,通过组合子问题的解来求解原问题。关键是 状态转移方程,即如何由已求出的局部最优解来推导全局最优解,全局最优解一定包含某个局部最优解,但不一定包含前一个局部最优解,因此需要记录之前的所有最优解。边界条件 是最简单的,可以直接得出的局部最优解。
  • 贪心算法:自顶向下,进行一次次选择,将给定问题变得更小。从问题的某一个初始解出发逐步逼近给定的目标,总是做出当时看来最佳的选择,由上一步的最优解推导下一步的最优解,因此只需要记录上一步的最优解。

动态规划的核心就是 “穷举”,因为要找 “最值”,肯定要把所有可能情况都列出来,才能找最值呀。但这里的穷举不是真的 “老实人穷举法”,一般这类问题都存在 “重叠子问题”,通过 “备忘录” 或者 “DP table” 可以优化穷举过程,避免重复的计算。

动态规划的 3 个核心:① 重叠子问题,② 最优子结构,③ 状态转移方程。


参考文章:
【1】动态规划 LeetCode 题解,总结了各种经典的DP题目
【2】动态规划系列,搭建动态规划思维框架

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

不吃饭就会放大招

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值