动态规划(DP,Dynamic Programing)专项训练

登录以参加训练计划

动态规划思维模板逻辑

这张思维导图展示了一套非常有条理的动态规划(Dynamic Programming, DP)学习路径,特别强调了从一维数组/字符串图论的递进关系。

这种分类方式(如“左右找子结构”、“中间找子结构”等)是该特定课程(志宏说算法)的教学术语,本质上对应了算法竞赛中经典的DP模型(如线性DP、区间DP、背包问题、状压DP等)。

下面我按照图中的分类,为你整理了对应的 洛谷(Luogu) 经典题目,帮助你按图索骥进行训练。


第一部分:一维数组类 / 字符串类 (线性DP与背包)

这部分是DP的基础,主要解决“由前一个状态推导当前状态”的问题。

1. 左右找子结构 & 找1个子数组

核心逻辑dp[i]dp[i] 通常只与 dp[i1]dp[i-1] 或前几个状态有关。对应经典的“最大子序和”模型。

  • P1115 最大子段和(最经典的“找1个子数组”问题,必做)
  • P1002 [NOIP2002 普及组] 过河卒(基础的网格路径计数,线性推导)
  • P1216 [USACO1.5][IOI1994] 数字三角形 Number Triangles(经典的自上而下或自下而上推导)

2. 01背包问题 (属于“左右找子结构”的变种)

核心逻辑:选或不选,状态转移依赖于剩余容量。

  • P1048 [NOIP2005 普及组] 采药(最标准的01背包模板题)
  • P2871 [USACO07DEC] Charm Bracelet S(01背包标准题)
  • P1060 [NOIP2006 普及组] 开心的金明(01背包变种)
  • P1049 [NOIP2001 普及组] 装箱问题(求最小剩余空间,本质还是01背包)

3. 股票买卖问题

核心逻辑:状态机模型,每一天持有或不持有股票。 (注:洛谷上纯粹的股票题较少,这类题目在 LeetCode 上最全[121, 122, 123, 188等],但在洛谷可以用类似的线性状态机题目替代)

  • P1420 最长连号(虽然简单,但体现了线性扫描的思维)
  • P1969 [NOIP2011 提高组] 积木大赛(贪心/线性递推,思想类似)
  • 建议去 LeetCode 刷:121. 买卖股票的最佳时机 等系列

4. 中间找子结构 (通常指 LIS 模型)

核心逻辑dp[i]dp[i] 需要扫描 00i1i-1 的所有状态来寻找最优解。最典型的是“最长上升子序列”。

  • P1020 [NOIP1999 普及组] 导弹拦截(最长上升/不上升子序列,经典必做)
  • P1091 [NOIP2004 提高组] 合唱队形(正向LIS + 反向LIS,经典拼接)
  • P1439 【模板】最长公共子序列(虽然名字是LCS,但转化后其实是LIS的O(nlogn)O(nlogn)解法)

5. 两边找子结构 (区间 DP)

核心逻辑:大区间 [i,j][i, j] 的最优解依赖于小区间 [i+1,j][i+1, j][i,j1][i, j-1][i,k]+[k+1,j][i, k] + [k+1, j]。即区间动态规划

  • P1880 [NOI1995] 石子合并(区间DP祖师爷级别的题目,环形处理)
  • P1063 [NOIP2006 提高组] 能量项链(环形区间DP)
  • P3205 [HNOI2010] 合唱队(区间DP,考虑左右端点进队顺序)
  • P4170 [CQOI2007] 涂色(经典的区间覆盖染色问题)

6. 两个数组 (LCS / 编辑距离)

核心逻辑dp[i][j]dp[i][j] 表示数组A的前 ii 个和数组B的前 jj 个匹配的结果。

  • P1439 【模板】最长公共子序列(前面提过,如果是 O(n2)O(n^2) 朴素做法就是这类,虽然该题数据要求更高)
  • P2758 编辑距离(经典的两个字符串转换步数)
  • P1140 相似基因(带权值的LCS变种)

7. 子集找子结构 (划分子集 / 子集和)

核心逻辑:通常涉及将集合划分为满足条件的子集,或者背包问题的变种。

  • P1019 [NOIP2000 提高组] 单词接龙(虽然常搜做,但包含子结构拼接思想)
  • P1164 小A点菜(01背包求方案数)
  • P2392 kkksc03考前临时抱佛脚(搜索+剪枝,或者看作极小数据的子集划分DP)

第二部分:图类 (图论与DP的结合)

这部分对应图中的右侧分支,难度通常高于纯数组类DP。

1. 单源带条件最短路径 (分层图 / DP on Graph)

核心逻辑:在求最短路的基础上增加了“k次免费”、“油量限制”或“状态限制”。

  • P4568 [JLOI2011] 飞行路线(分层图最短路,本质是状态机DP思想在图上的应用,k次免费机会)
  • P1073 [NOIP2009 提高组] 最优贸易(在图上进行买卖,结合了SPFA/Dijkstra和DP思想)
  • P3953 [NOIP2017 提高组] 逛公园(在图上进行DP计数,求k短路相关)
  • P1462 通往奥格瑞玛的道路(二分答案 + 最短路 check)

2. 经过所有节点的路径 (状压 DP / TSP 问题)

核心逻辑:数据范围通常 N20N \le 20,需要用二进制位来表示“哪些节点走过,哪些没走过”。

  • P1433 吃奶酪(经典的TSP旅行商问题,状压DP)
  • P1171 售货员的难题(标准的TSP问题)
  • P1896 [SCOI2005] 互不侵犯(状压DP入门,虽然不是路径,但是状态压缩思想一致)
  • P2915 [USACO08NOV] Mixed Up Cows G(排列型状压DP)

学习建议

  1. 按顺序刷:先搞定“一维数组类”,尤其是最大子段和01背包,这是所有DP的基石。
  2. 重模板:图中的分类其实就是模板。比如做“区间DP”时,脑子里要有 for len, for i, for k 的三层循环结构。
  3. 看题解:如果卡住了,洛谷的题解区非常丰富,重点看那些解释了 “状态定义”(即 dp[i]dp[i] 代表什么)和 “状态转移方程” 的题解。

祝你刷题愉快,早日攻克DP算法题!

这里面没有“树上的DP”吗?

你观察得非常仔细!这张思维导图中确实 没有明确列出“树形 DP”(Tree DP) 这一板块。

这张图主要聚焦在线性 DP(数组/字符串)和图论 DP(最短路/状压)上。然而,在算法竞赛(NOIP/CSP/ICPC)以及大厂面试中,树形 DP 是绝对的重点,甚至比复杂的图论 DP 考频更高。

为了补全你的学习拼图,我为你单独整理了树形 DP 的核心逻辑和洛谷经典题目


补全板块:树形 DP (Tree DP)

核心逻辑: 树形 DP 的本质是在 树(或森林) 的数据结构上进行动态规划。 通常的套路是:DFS(深度优先搜索)

  1. 自底向上:先递归处理子节点(子树),算出子节点的状态。
  2. 状态合并:将子节点的信息汇总给父节点,从而更新父节点的状态。
  3. 状态定义dp[u][state]dp[u][state] 通常表示“以节点 uu 为根的子树,处于 statestate 状态下的最优解”。

1. 入门模板:最大独立集 / 染色问题

核心逻辑:当前节点 uu 选或不选,会限制子节点 vv 的选择。

  • dp[u][0]dp[u][0]uu 不选,子节点 vv 可选可不选。

  • dp[u][1]dp[u][1]uu 选,子节点 vv 绝不能选。

  • P1352 没有上司的舞会必做,树形DP的“Hello World”,核心是父子不能同时出现)

  • P1122 最大子树和(稍微变化,修剪枝叶,求权值最大的连通子块)

  • P2016 战略游戏(最小点覆盖,和舞会题逻辑互补)

2. 树上背包 (树形依赖背包)

核心逻辑:在树上做“01背包”或“分组背包”。 通常 dp[u][k]dp[u][k] 表示以 uu 为根的子树中,选了 kk 个节点/体积的最大价值。因为要分配 kk 给各个子树,通常需要两层循环(类似卷积),时间复杂度 O(n2)O(n^2)O(n3)O(n^3)

  • P2014 [CTSC1997] 选课必做,树上背包的祖师爷,选了子节点必须选父节点)
  • P2015 二叉苹果树(保留 QQ 根树枝,其实就是保留 Q+1Q+1 个节点,标准树上背包)
  • P1273 有线电视网(分组背包模型,求不亏本的最大用户数)

3. 树的直径与中心

核心逻辑:在树上找最长路径。 通常维护两个值:向下延伸的最长链和次长链。

  • P1351 [NOIP2014 提高组] 联合权值(虽然可以用数学方法,但树形DP思维也可以解)
  • P1099 [NOIP2007 提高组] 树网的核(求树的直径及其相关性质)

4. 换根 DP (二次扫描法)

核心逻辑:这是树形DP的进阶。 先假设 1 为根做一次 DFS(自底向上),算出所有节点的子树贡献; 再做第二次 DFS(自顶向下),算出“父亲方向”对当前节点的贡献,从而求出以任意节点为根时的答案。

  • P3478 [POI2008] STA-Station必做,换根DP模板题,求以谁为根深度和最大)
  • P2986 [USACO10MAR] Great Cow Gathering G(带权值的换根DP)
  • P1364 医院设置(数据范围小可用 Floyd,数据大则必须用换根 DP)

总结建议

如果你按照那张图学习,在学完 “一维数组类”“子集找子结构” 之后,建议立刻插入“树形 DP”的学习,然后再去学右边的“图类”。

因为树形 DP 实际上是“子集找子结构”在树这种特殊图上的应用,难度介于线性 DP 和 状压 DP 之间,是承上启下的关键环节。


树上DP有哪些洛谷入门题?

你好!很高兴看到你开始攻克树形DP。这是动态规划与图论结合的第一步,也是联赛(NOIP/CSP-S)中非常高频的考点。

树形DP的核心思想其实只有一句话:父亲的状态由子节点的状态转移而来(自底向上)。 代码实现上,通常使用 DFS(后序遍历)。

我为你精选了洛谷上最适合入门的几道题目,并按题型模式进行了分类。请按顺序练习。


第一阶段:经典的“选与不选”模型

这是树形DP最基础的模型,状态通常定义为 dp[u][0]dp[u][0](不选 uu)和 dp[u][1]dp[u][1](选 uu)。

1. P1352 [USACO05NOV] 没有上司的舞会

  • 难度:🟡 普及/提高-
  • 一句话题意:给一棵树,每个点有快乐值。选了某个点,就不能选它的直接父节点。求最大快乐值。
  • 教练点评这是树形DP的“Hello World”,绝对的板子题。
  • 核心方程
    • uu:子节点 vv 必定不能选 dp[u][1]+=dp[v][0]\to dp[u][1] += dp[v][0]
    • 不选 uu:子节点 vv 可选可不选(取最大)dp[u][0]+=max(dp[v][0],dp[v][1])\to dp[u][0] += \max(dp[v][0], dp[v][1])

2. P2016 战略游戏

  • 难度:🟡 普及/提高-
  • 一句话题意:给一棵树,在节点上放士兵,一个士兵可以看守与该节点相连的所有边。求最少放多少士兵能看守所有边。
  • 教练点评:这是最小点覆盖问题。跟上一题是对偶关系。
  • 思路提示
    • uu:子节点 vv 选不选都可以,取花费少的。
    • 不选 uu:为了看守 (u,v)(u, v) 这条边,子节点 vv 必须选。

3. P1122 最大子树和

  • 难度:🟡 普及/提高-
  • 一句话题意:树上每个点有权值(可能为负),求一个连通子树,使得点权之和最大。
  • 教练点评:这题不需要二维数组。思路非常贪心——如果子树贡献是正的就要,负的就扔掉。

第二阶段:树上背包(泛化物品背包)

这种题目通常限制选 MM 个节点/边,或者有体积限制。其实就是把背包问题搬到了树上:把子树看作是物品组

4. P2015 二叉苹果树

  • 难度:🟢 普及+/提高
  • 一句话题意:保留树上 QQ 根树枝,使得留下的苹果最多。
  • 教练点评:树上背包的入门题。因为是二叉树,所以转移方程比较好写(枚举给左儿子分多少根树枝,右儿子分多少)。
  • 状态定义dp[u][j]dp[u][j] 表示以 uu 为根的子树中,保留 jj 条边能得到的最大值。

5. P2014 [CTSC1997] 选课

  • 难度:🟢 普及+/提高
  • 一句话题意:选课有先修关系(形成森林),每门课有学分。限制选 MM 门课,求最大通常。
  • 教练点评树上背包的必修课
  • 技巧
    1. 题目给的是森林(多棵树),需要建立一个虚拟根节点 0 把它们连成一棵大树。
    2. 这是多叉树,需要用类似“分组背包”的思路:枚举给当前子节点 vv 分配多少体积 kk
    3. 时间复杂度是 O(NM2)O(N \cdot M^2) 或优化后的 O(NM)O(N \cdot M)

第三阶段:树的直径与中心(路径相关)

这类题目关注树上最长的路径或特定的节点性质。

6. P1351 [NOIP2014 提高组] 联合权值

  • 难度:🟢 普及+/提高
  • 一句话题意:求树上距离为 2 的所有点对的权值乘积之和及最大值。
  • 教练点评:这题其实可以用简单的遍历解决,但它蕴含了树形DP处理子树信息的思想(维护最大值和次大值)。

7. P1099 [NOIP2007 提高组] 树网的核

  • 难度:🔵 提高+/省选-
  • 一句话题意:涉及树的直径和偏心距。
  • 教练点评:虽然难度标得高,但核心是求树的直径。先学会怎么用两次 DFS 或 树形 DP 求直径,这题是进阶训练。

8. P1272 重建道路

  • 难度:🟢 普及+/提高
  • 一句话题意:切断最少的边,得到一个节点数为 PP 的子树。
  • 教练点评:这是一道计数类的树形DP。思考方向:dp[i][j]dp[i][j] 表示以 ii 为根,保留 jj 个节点的最小删边数。

教练的刷题建议

  1. 先做 P1352,如果你能独立写出这题,就理解了树形DP的 50%。
  2. 再做 P2014,这是树上背包的通解模板,学会了这个,P2015 就迎刃而解了。
  3. 注意边界:树形DP容易在叶子节点或根节点处写错边界,要在草稿纸上模拟一下叶子节点的返回值。
  4. 建图:记得用邻接表(vector<int> G[N] 或 链式前向星)存图,题目通常是无向边,DP时要传入 father 参数防止死循环。

解释前面说的LIS 模型

LIS (Longest Increasing Subsequence),即最长上升子序列

在之前的思维导图中,它被归类为“中间找子结构”。这是一个非常形象的描述,因为它揭示了 LIS 模型与基础 DP(如最大子段和)的核心区别。

下面我为你拆解这个模型的核心逻辑、为什么叫“中间找”,以及它的代码模板。


1. 什么是“子序列”?

首先要区分两个概念,这是新手的易错点:

  • 子数组/子串 (Subarray/Substring):必须是连续的。
    • 例子:[10, 9, 2, 5] 的子数组是 [9, 2]
  • 子序列 (Subsequence):可以是不连续的,但相对顺序不能变。
    • 例子:[10, 9, 2, 5, 3, 7, 101, 18]
    • 它的一个上升子序列是:[2, 5, 7, 101]
    • 另一个上升子序列是:[2, 3, 7, 18]

LIS 问题就是: 在一个给定的数组中,找到一个最长的子序列,使得这个子序列中的元素是严格递增的。


2. 为什么叫“中间找子结构”?

回顾一下 “左右找子结构”(比如最大子段和):

  • 计算 dp[i]dp[i] 时,我们通常只需要看 dp[i1]dp[i-1](它左边的紧邻邻居)。

而在 LIS 模型中:

  • 为了计算以第 ii 个数字结尾的最长子序列长度 dp[i]dp[i],仅仅看 dp[i1]dp[i-1] 是不够的。
  • 你需要回头扫描 00i1i-1 之间的所有位置 jj
  • 只要 nums[j]<nums[i]nums[j] < nums[i],说明 nums[i]nums[i] 可以接在 nums[j]nums[j] 后面。
  • 我们要从这些能接的位置里,挑一个本来就最长的。

因为这种 “回头看所有前面状态” 的特性,所以被称为“中间找子结构”或“扫描式 DP”。

为了回看“所有前面的状态”,就需要 使用二维数组把状态记忆化 以及 从简单的初始边界条件开始递推 !


3. 核心逻辑与状态转移方程 (O(N2)O(N^2))

状态定义

dp[i]dp[i] 表示:必须以 nums[i] 这个数结尾的最长上升子序列的长度。 (注意:一定是包含 nums[i] 的)

状态转移方程

对于每一个 ii,我们需要遍历 jj (0j<i0 \le j < i):

$$dp[i] = \max(dp[j]) + 1, \quad \text{其中 } nums[j] < nums[i] $$
  • 如果找不到任何比 nums[i]nums[i] 小的 nums[j]nums[j],则 dp[i]=1dp[i] = 1(只有它自己)。

最终答案

答案不是 dp[n1]dp[n-1],而是整个 dpdp 数组中的最大值:max(dp[0n1])\max(dp[0 \dots n-1])


4. 代码模板 (C++)

这是最基础的 O(N2)O(N^2) 写法,也是理解 DP 思想的最佳模板。

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;

int main() {
    int n;
    cin >> n;
    vector<int> nums(n);
    for(int i = 0; i < n; i++) cin >> nums[i];

    // dp[i] 初始化为 1,因为每个元素本身至少长度为 1
    vector<int> dp(n, 1);
    int ans = 1; // 记录全局最大值

    for (int i = 1; i < n; i++) {       // 枚举当前结尾的元素
        for (int j = 0; j < i; j++) {   // “中间找”:回头扫描前面的元素
            if (nums[j] < nums[i]) {    // 如果能接上
                dp[i] = max(dp[i], dp[j] + 1);
            }
        }
        ans = max(ans, dp[i]); // 更新全局最大值
    }

    cout << ans << endl;
    return 0;
}

5. 进阶:O(NlogN)O(N \log N) 贪心 + 二分法

在实际面试或竞赛中,如果数据范围 N>5000N > 5000,上面的 O(N2)O(N^2) 会超时。LIS 有一个经典的优化解法,虽不属于纯 DP,但非常重要。

核心思想(贪心):

  • 如果我们要让上升子序列尽可能长,那么序列中的数字应该尽可能小,这样后面才容易接上更大的数。
  • 我们维护一个数组 tails,其中 tails[k] 存储长度为 k+1 的上升子序列的最小结尾元素
  • 遍历 nums 时,通过二分查找更新 tails 数组。

(这也是洛谷 P1020 导弹拦截 必须掌握的解法)


6. LIS 模型的经典变种

理解了 LIS,你就能解决一系列变种题:

  1. 最长不下降子序列
    • 条件变成 nums[j]nums[i]nums[j] \le nums[i]
  2. 合唱队形 (洛谷 P1091)
    • 先上升后下降。
    • 解法:求一遍正向 LIS (dp1dp1),再求一遍反向 LIS (dp2dp2),答案就是 max(dp1[i]+dp2[i]1)\max(dp1[i] + dp2[i] - 1)
  3. 俄罗斯套娃信封 (LeetCode 354)
    • 二维的 LIS。
    • 解法:先按宽度排序,如果宽度相同按高度降序,然后对高度求 LIS。
  4. 最少拦截系统 (Dilworth 定理)
    • 洛谷 P1020 的第二问。
    • 定理:一个序列的最少下降子序列划分数 = 该序列的最长上升子序列长度。

总结: LIS 模型是 DP 入门到进阶的必修课,它教会了我们 “状态不仅仅可以只看前一个,还可以回头看前面所有” 这一重要思维。


动态规划循序渐进洛谷题单2

作为OI金牌教练,我为你精心设计了这份动态规划题单,涵盖从入门到进阶的全部核心知识点。每个阶段都有明确的学习目标和精选题目,帮助你系统掌握DP思想。

🏆 学习建议

  • 每个阶段至少完成80%的题目再进入下一阶段
  • 先独立思考,再参考题解
  • 总结每道题的状态定义和转移方程
  • 定期回顾已做题目,加深理解

📚 第一阶段:线性DP(基础)

学习目标:掌握DP的基本思想,理解状态定义和转移方程
核心概念:状态、转移方程、边界条件、最优子结构

题目编号 题目名称 难度 知识点
P1216 数字三角形 普及- DP入门、递推
P1002 过河卒 普及/提高- 路径计数、无障碍DP
P1044 Catalan数、状态转移
P1025 数的划分 整数划分、状态设计
P1077 摆花 限制条件的计数DP
P1115 最大子段和 普及- 经典线性DP、状态优化
P1280 尼克的任务 普及/提高- 逆向思维DP
P1466 集合 Subset Sums 01背包思想的应用

🎒 第二阶段:背包问题(重点)

学习目标:掌握各类背包问题的建模和优化方法
核心概念:01背包、完全背包、多重背包、分组背包

题目编号 题目名称 难度 知识点
P1048 采药 普及- 01背包模板
P1616 疯狂的采药 普及/提高- 完全背包模板
P1060 开心的金明 01背包变形、价值最大化
P1064 金明的预算方案 提高/省选- 分组背包、依赖背包
P1833 樱花 多重背包优化
P1776 宝物筛选 二进制优化
P3188 [HNOI2007]梦幻岛宝珠 省选/NOI- 分组背包、状态压缩
P2925 [USACO08DEC]Patting Heads S 普及+/提高 完全背包思想的计数应用

📊 第三阶段:区间DP

学习目标:掌握区间上的动态规划问题
核心概念:区间状态定义、合并转移、区间枚举顺序

题目编号 题目名称 难度 知识点
P1435 回文字串 普及+/提高 最长回文子序列
P1220 关路灯 提高+/省选- 区间DP、状态记录位置
P1880 石子合并 提高/省选- 经典区间DP、环形处理
P4170 涂色 提高+/省选- 区间DP、状态合并
P2470 压缩 省选/NOI- 区间DP、状态设计
P3205 合唱队 提高+/省选- 区间DP、方向状态
P4302 道路相遇 省选/NOI- 区间DP、LCA

🌳 第四阶段:树形DP

学习目标:掌握在树上进行动态规划的方法
核心概念:子树状态、根节点转移、树的遍历顺序

题目编号 题目名称 难度 知识点
P1352 没有上司的舞会 普及+/提高 树形DP入门、选/不选
P1122 最大子树和 树形DP、子树贡献
P2015 二叉苹果树 提高/省选- 树形背包
P1273 有线电视网 提高+/省选- 树形DP、分组背包
P2458 保安站岗 树形DP、三种状态
P3174 [HAOI2009]毛毛虫 树形DP、最长链
P4211 树上的数 省选/NOI- 树形DP、状态设计

🎯 第五阶段:状态压缩DP

学习目标:掌握用二进制表示状态的动态规划方法
核心概念:状态压缩、位运算、状态转移优化

题目编号 题目名称 难度 知识点
P1433 吃奶酪 普及+/提高 状态压缩DP入门
P1896 互不侵犯 提高/省选- 状压DP、行转移
P2704 炮兵阵地 提高+/省选- 状压DP、状态压缩优化
P3694 邦邦的大合唱站队 状压DP、费用提前计算
P3195 玩具装箱 提高/省选- 单调队列优化DP
P4163 [SCOI2007]排列 省选/NOI- 状压DP、数位限制
P4640 [IOI2014]wall砖墙 状压DP、滚动数组

🔢 第六阶段:数位DP

学习目标:掌握处理数字计数问题的动态规划方法
核心概念:数位分解、状态记录、记忆化搜索

题目编号 题目名称 难度 知识点
P2602 数字计数 提高/省选- 数位DP入门
P3413 SAC#1 - 萌数 数位DP、回文判断
P4127 同类分布 提高+/省选- 数位DP、模运算
P4999 烦人的数学作业 提高/省选- 数位DP、数字和
P3281 [SCOI2013]数数 省选/NOI- 数位DP、高精度
P5104 红包发红包 数位DP、期望

⭐ 第七阶段:高级DP技巧

学习目标:掌握复杂问题的DP建模和优化方法
核心概念:优化技巧、多维DP、状态设计

题目编号 题目名称 难度 知识点
P2051 中国象棋 提高+/省选- 状态压缩、二维DP
P2150 寿司晚宴 省选/NOI- 状压DP、博弈论
P3206 [HNOI2010]城市建设 动态树分治、DP
P4363 [九省联考2018]一双木棋 状压DP、博弈论
P5020 货币系统 提高+/省选- 完全背包、数学优化
P5325 [BJOI2019]删数 省选/NOI- 区间DP、栈优化

📈 进阶挑战:NOI/IOI真题

完成前七个阶段后,可以挑战这些更高难度的题目:

题目编号 题目名称 难度
P4052 环形珍珠 NOI/IOI-
P4290 玩具装箱
P5023 树屋阶梯
P5158 [USACO18DEC]Convention II
P5298 [PKUWC2018]Minimax

💡 教练寄语

  • 动态规划的核心是状态定义转移方程,这需要大量练习来培养直觉
  • 遇到难题时,先尝试简化问题,再逐步增加复杂度
  • 学会从问题中抽象出DP模型,这是DP学习的关键
  • 定期总结不同类型DP的共性和特点,形成自己的知识体系

祝你在动态规划的学习道路上越走越远!🏆

章节 1. 一维数组(字符串)上的DP

开放

题目 尝试 AC 难度
luoguP10250   [GESP样题 六级] 下楼梯 1 1 3
luoguB3637   最长上升子序列 1 1 3
luoguP10287   [GESP样题 七级] 最长不下降子序列 1 1 5
luoguP1091   [NOIP 2004 提高组] 合唱队形 1 1 3
luoguP1020   [NOIP 1999 提高组] 导弹拦截 1 1 6

章节 2. 01背包的DP

开放

题目 尝试 AC 难度
4230   0-1 背包问题(动态规划) 1 1 10
19255   线粒体的能量预算 1 1 10

章节 3. 二维数组上的DP

开放

题目 尝试 AC 难度
696   栈【2003NOIP普及组 catalan数概念】 12 4 9

章节 4. 树上的DP

开放

题目 尝试 AC 难度
2170   没有上司的舞会 1 1 10
19298   推恩令的赏赐 1 1 10
luoguP2016   战略游戏 1 1 5
luoguP1122   最大子树和 1 0 5
luoguP2015   二叉苹果树 1 1 6
luoguP2014   [CTSC1997] 选课 1 1 6

章节 5. 图上的DP

开放

题目 尝试 AC 难度
19300   木牛流马的征途 1 1 10