林老师 · 客观题题库 · 第 17 章 动态规划入门 · 知识细节练习

第 17 章 动态规划入门 · 知识细节练习

100 题 · 每题对应一个知识细节 · 全部原创
真题
复刻
试卷编号ORIG-第17章动态规划入门-知识细节练习
题目总数100 题 · 100 分
试卷类型客观题
考生须知:
① 本卷共 16 大部分,合计 100 题 · 100 分,全部为客观题;
② 试卷右上角设有 「提交答卷」「重置考试」 按钮,提交后系统自动判分并显示答题正确情况,请确认全部作答后再行提交;
③ 试卷不显示答案,提交后方可查看每题作答与正确答案的对照;
④ 答卷进度会保留在本地缓存中,刷新或再次打开仍可继续作答;
⑤ 本卷仅供学生练习使用;请勿用于其他用途;题面有问题请联系:i64coder@163.com。

判 分 报 告

0 / 100 分
0
答 对 · 得 0
0
答 错 · 失 0
当前筛选下没有题目

DP 基本概念

6 QUESTIONS · 2 POINTS EACH
第 1 题 A1 未作答

判断题:动态规划(DP)= 把问题拆成子问题、每个子问题只算一次并记录,由小到大组合出答案——适用前提是最优子结构 + 重叠子问题。

(1 分)
第 2 题 A2 未作答

判断题:DP 的三要素:状态f 数组表示什么)、转移(怎么由小状态算出大状态)、初始化(最小状态的初值)。

(1 分)
第 3 题 A3 未作答

判断题:初始化错误会让整张 DP 表错——例如"恰好装满"的背包没有把"不可达容量"设成 -∞,就会把非法状态当合法。

(1 分)
第 4 题 A4 未作答

判断题:贪心每步只做一个选择;DP 尝试所有转移取最优——DP 更"全面",但要求状态能编号、转移满足无后效性。

(1 分)
第 5 题 A5 未作答

判断题:递推是 DP 的雏形:DP 的"状态 + 转移"就是递推的"数组 + 公式",DP 多了"取 max/min 的最优决策"。

(1 分)
第 6 题 A6 未作答

判断题:做 DP 的标准四步:① 定义状态 ② 写转移方程 ③ 定初始化 ④ 找答案位置。

(1 分)

一维 DP 经典

7 QUESTIONS · 2 POINTS EACH
第 7 题 B1 未作答

单选题:爬楼梯 f(n)=f(n1)+f(n2)f(n) = f(n-1) + f(n-2)f(1)=1f(1)=1f(2)=2f(2)=2f(10)f(10) 的值是?

(1 分)
第 8 题 B2 未作答

判断题:最大子段和的一维 DP:f[i] = max(f[i-1] + a[i], a[i])——"接在前一段后面"或"以 a[i] 重新开始"。

(1 分)
第 9 题 B3 未作答

单选题:数字三角形自顶向下走(每步左下或右下),第 ii 行第 jj 列的状态由上一行的哪两个状态转移而来?

(1 分)
第 10 题 B4 未作答

判断题:网格从 (0,0)(0,0) 只能向右/下走到 (n,m)(n, m),路径数 f[i][j]=f[i1][j]+f[i][j1]f[i][j] = f[i-1][j] + f[i][j-1]f[0][0]=1f[0][0] = 1

(1 分)
第 11 题 B5 未作答

判断题:LIS(最长上升子序列)= 从序列中按原顺序选出、不必连续的最长严格递增子序列。

(1 分)
第 12 题 B6 未作答

单选题:一排数选若干个数使和最大、且不能选相邻两个,f[i]f[i] 表示前 ii 个数的最优解,转移是?

(1 分)
第 13 题 B7 未作答

判断题:一维 DP 若 f[i]f[i] 只依赖 f[i1]f[i-1]f[i2]f[i-2],可用滚动变量把空间从 O(n)O(n) 降到 O(1)O(1)

(1 分)

01 背包

7 QUESTIONS · 2 POINTS EACH
第 14 题 C1 未作答

单选题:01 背包(NN 件物品、重量 wiw_i、价值 viv_i、容量 CC、每件最多选 1 次),状态 f[i][j]f[i][j] 表示?

(1 分)
第 15 题 C2 未作答

单选题:01 背包对第 ii 件物品(重量 ww、价值 vv)的转移是?

(1 分)
第 16 题 C3 未作答

判断题:滚动数组版 01 背包的容量循环必须倒序jCCww)——正序会让同一件物品被选多次。

(1 分)
第 17 题 C4 未作答

判断题:"恰好装满"要求初始化 f[0]=0f[0]=0、其余为 -∞(或极小值)——装不满的容量状态保持"不可达"。

(1 分)
第 18 题 C5 未作答

判断题:"不超过容量"(装不满也算合法)时初始化全部为 00 即可。

(1 分)
第 19 题 C6 未作答

单选题:求"恰好装满容量 jj 的方案数",滚动数组的转移是?

(1 分)
第 20 题 C7 未作答

判断题:01 背包不能用贪心(按单位价值排序会错)——第 15 章的 0/1 背包反例正是 DP 的用武之地。

(1 分)

二维 DP 概念

7 QUESTIONS · 2 POINTS EACH
第 21 题 D1 未作答

判断题:二维 DP 的状态是 f[i][j]——"走到/处理到第 ii 行第 jj 列时……",常见于网格路径类问题。

(1 分)
第 22 题 D2 未作答

判断题:nimesmn imes m 矩阵从 (0,0)(0,0)(n1,m1)(n-1, m-1) 只能向右/下走,最大路径和:f[i][j]=max(f[i1][j],f[i][j1])+a[i][j]f[i][j] = \max(f[i-1][j], f[i][j-1]) + a[i][j]

(1 分)
第 23 题 D3 未作答

单选题:矩阵路径 DP 中 f[i][j]f[i][j] 由哪两个状态转移而来?

(1 分)
第 24 题 D4 未作答

判断题:矩阵路径 DP 中,第一行只能从左方来、第一列只能从上方来——边界行/列的转移要特判,否则会越界读状态。

(1 分)
第 25 题 D5 未作答

判断题:有障碍的网格:计数 DP 中障碍格的路径数记为 00(不可达),转移时跳过障碍格。

(1 分)
第 26 题 D6 未作答

单选题:nimesmn imes m 矩阵的二维 DP 时间复杂度是?

(1 分)
第 27 题 D7 未作答

判断题:二维 DP 可以逐行滚动:只保留上一行数组,空间从 O(nm)O(nm) 降到 O(m)O(m)

(1 分)

LIS 专题

6 QUESTIONS · 2 POINTS EACH
第 28 题 E1 未作答

判断题:LIS 要求严格递增(转移条件 a[j]<a[i]a[j] < a[i]);把条件放宽为 a[j]a[i]a[j] \leq a[i] 就是最长不下降子序列(LNDS)。

(1 分)
第 29 题 E2 未作答

单选题:LIS 的 O(n2)O(n^2) 转移中,f[i]f[i] 的初值应是?

(1 分)
第 30 题 E3 未作答

单选题:LIS 的长度是?

(1 分)
第 31 题 E4 未作答

判断题:记录 pre[i]f[i]f[i] 由哪个 jj 转移来),从答案位置沿 pre 倒推,即可还原出一条 LIS。

(1 分)
第 32 题 E5 未作答

判断题:子序列不必连续(如 LIS),子段/子数组必须连续(如最大子段和)——两个概念要分清。

(1 分)
第 33 题 E6 未作答

判断题:最长长度相同的 LIS 可能有多条(不同元素组成)——题目问方案时注意按规则去重。

(1 分)

DP 与其它算法

6 QUESTIONS · 2 POINTS EACH
第 34 题 F1 未作答

判断题:分治的子问题独立不重叠;DP 的子问题大量重叠——这是两者适用场景的分界。

(1 分)
第 35 题 F2 未作答

判断题:回溯指数级枚举所有方案;DP 记录每个状态的最优值、避免重复计算——规模大时 DP 是回溯的"高效版"。

(1 分)
第 36 题 F3 未作答

判断题:DP 的时间复杂度 = 状态数 × 每个状态的转移代价。

(1 分)
第 37 题 F4 未作答

判断题:DP 常见错误:状态定义不清、转移漏分支(如漏"不选")、初始化错、答案位置取错。

(1 分)
第 38 题 F5 未作答

单选题:以下哪类问题不满足最优子结构(子问题最优拼不出全局最优)?

(1 分)
第 39 题 F6 未作答

判断题:nn 很小时可以用暴力枚举验证 DP 结果(对拍);nn 大时 DP 才是可行方案。

(1 分)

实战细节

6 QUESTIONS · 2 POINTS EACH
第 40 题 G1 未作答

判断题:状态设计三问:状态装得下(数组够大)、转移要简单、答案要取得到。

(1 分)
第 41 题 G2 未作答

判断题:转移顺序必须保证"用到的状态先算好"(拓扑序)——背包按容量从小到大、二维 DP 按行从上到下。

(1 分)
第 42 题 G3 未作答

判断题:答案可能在 f[n][m]max(f[n][*]) 或全部状态的最大值——按题目定义取。

(1 分)
第 43 题 G4 未作答

判断题:DP 数组要开"状态最大值 + 1"(防止下标越界),越界是 DP 题最常见的崩溃点之一。

(1 分)
第 44 题 G5 未作答

单选题:01 背包转移中当 j < w(容量放不下当前物品)时,应该?

(1 分)
第 45 题 G6 未作答

判断题:调试 DP 的实用方法:打印整张 DP 表,与小数据手算结果对照,能快速定位状态/转移/初始化错误。

(1 分)

易错综合

5 QUESTIONS · 2 POINTS EACH
第 46 题 H1 未作答

单选题:滚动数组 01 背包把容量循环写成正序,后果是?

(1 分)
第 47 题 H2 未作答

单选题:"恰好装满"背包却用全 00 初始化,会?

(1 分)
第 48 题 H3 未作答

单选题:01 背包转移只写"选"分支、漏了"不选"分支,会?

(1 分)
第 49 题 H4 未作答

单选题:LIS 最长子序列不以最后一个元素结尾时,正确做法是?

(1 分)
第 50 题 H5 未作答

判断题:以下结论全部正确——"DP 三要素是状态/转移/初始化;01 背包滚动数组容量倒序;LIS 答案取最大值;数字三角形逐行填表"。

(1 分)

一维 DP 代码

7 QUESTIONS · 2 POINTS EACH
第 51 题 I1 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int f[15];
05    f[1] = 1; f[2] = 2;                  // 爬楼梯初始化
06    for (int i = 3; i <= 10; i++)
07        f[i] = f[i - 1] + f[i - 2];      // 转移
08    cout << f[10];
09    return 0;
10}

单选题:程序输出是?

(1 分)
第 52 题 I2 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[6] = {-2, 1, -3, 4, -1, 2};
05    int f[6], best;
06    f[0] = a[0]; best = f[0];
07    for (int i = 1; i < 6; i++) {
08        f[i] = max(f[i - 1] + a[i], a[i]);   // 接上 / 重新开始
09        best = max(best, f[i]);
10    }
11    cout << best;                            // 最大子段和
12    return 0;
13}

单选题:程序输出是?

(1 分)
第 53 题 I3 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{3, 0, 0}, {1, 5, 0}, {8, 6, 7}};   // 3 层数字三角形
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 1; i < 3; i++)
08        for (int j = 0; j <= i; j++) {
09            f[i][j] = a[i][j];
10            if (j > 0) f[i][j] = max(f[i][j], f[i - 1][j - 1] + a[i][j]);
11            if (j < i) f[i][j] = max(f[i][j], f[i - 1][j] + a[i][j]);
12        }
13    cout << max({f[2][0], f[2][1], f[2][2]});          // 最后一行最大值
14    return 0;
15}

单选题:程序输出是?

(1 分)
第 54 题 I4 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int f[3][3] = {0};                   // 3x3 网格,只能向右/下
05    f[0][0] = 1;
06    for (int i = 0; i < 3; i++)
07        for (int j = 0; j < 3; j++) {
08            if (i > 0) f[i][j] += f[i - 1][j];
09            if (j > 0) f[i][j] += f[i][j - 1];
10        }
11    cout << f[2][2];                     // 从 (0,0) 到 (2,2) 的路径数
12    return 0;
13}

单选题:程序输出是?

(1 分)
第 55 题 I5 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[5] = {3, 2, 5, 10, 7};
05    int f[5];
06    f[0] = a[0];
07    f[1] = max(a[0], a[1]);
08    for (int i = 2; i < 5; i++)
09        f[i] = max(f[i - 1], f[i - 2] + a[i]);   // 不选 / 选(跳过前一个)
10    cout << f[4];
11    return 0;
12}

单选题:程序输出是?

(1 分)
第 56 题 I6 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    long long a = 1, b = 1;              // 滚动变量
05    for (int i = 3; i <= 10; i++) {
06        long long c = a + b;
07        a = b; b = c;
08    }
09    cout << b;
10    return 0;
11}

单选题:程序输出是?

(1 分)
第 57 题 I7 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int cost[6] = {0, 2, 3, 1, 5, 4};   // cost[i]:第 i 级台阶的费用
05    int f[6] = {0};
06    f[1] = cost[1];
07    f[2] = cost[2];
08    for (int i = 3; i <= 5; i++)
09        f[i] = min(f[i - 1], f[i - 2]) + cost[i];   // 从上一级或上上级来
10    cout << f[5];
11    return 0;
12}

单选题:程序输出是?

(1 分)

LIS 代码

6 QUESTIONS · 2 POINTS EACH
第 58 题 J1 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[8] = {3, 1, 4, 1, 5, 9, 2, 6};
05    int f[8], ans = 1;
06    for (int i = 0; i < 8; i++) {
07        f[i] = 1;                        // 初值:自己一个
08        for (int j = 0; j < i; j++)
09            if (a[j] < a[i]) f[i] = max(f[i], f[j] + 1);
10        ans = max(ans, f[i]);
11    }
12    cout << ans;                         // LIS 长度
13    return 0;
14}

单选题:程序输出是?

(1 分)
第 59 题 J2 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[5] = {3, 1, 4, 1, 5};
05    int f[5];
06    for (int i = 0; i < 5; i++) {
07        f[i] = 1;
08        for (int j = 0; j < i; j++)
09            if (a[j] < a[i]) f[i] = max(f[i], f[j] + 1);
10    }
11    for (int i = 0; i < 5; i++) cout << f[i] << " ";   // 输出每个 f[i]
12    return 0;
13}

单选题:程序输出是?

(1 分)
第 60 题 J3 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[5] = {1, 3, 3, 5, 2};
05    int f[5], ans = 1;
06    for (int i = 0; i < 5; i++) {
07        f[i] = 1;
08        for (int j = 0; j < i; j++)
09            if (a[j] <= a[i]) f[i] = max(f[i], f[j] + 1);   // 不下降:允许相等
10        ans = max(ans, f[i]);
11    }
12    cout << ans;                         // 最长不下降子序列长度
13    return 0;
14}

单选题:程序输出是?

(1 分)
第 61 题 J4 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[6] = {9, 4, 7, 2, 5, 1};
05    int f[6], ans = 1;
06    for (int i = 0; i < 6; i++) {
07        f[i] = 1;
08        for (int j = 0; j < i; j++)
09            if (a[j] > a[i]) f[i] = max(f[i], f[j] + 1);   // 严格下降
10        ans = max(ans, f[i]);
11    }
12    cout << ans;                         // 最长下降子序列长度
13    return 0;
14}

单选题:程序输出是?

(1 分)
第 62 题 J5 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[5] = {2, 1, 5, 3, 4};
05    int f[5], pre[5], ans = 1, pos = 0;
06    for (int i = 0; i < 5; i++) {
07        f[i] = 1; pre[i] = -1;
08        for (int j = 0; j < i; j++)
09            if (a[j] < a[i] && f[j] + 1 > f[i]) { f[i] = f[j] + 1; pre[i] = j; }
10        if (f[i] > ans) { ans = f[i]; pos = i; }
11    }
12    vector<int> seq;                     // 沿 pre 回溯还原 LIS
13    for (int x = pos; x != -1; x = pre[x]) seq.push_back(a[x]);
14    for (int i = seq.size() - 1; i >= 0; i--) cout << seq[i] << " ";
15    return 0;
16}

单选题:程序输出是?

(1 分)
第 63 题 J6 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[5] = {5, 1, 2, 3, 4};
05    int f[5], lis = 1;
06    for (int i = 0; i < 5; i++) {        // LIS:不要求连续
07        f[i] = 1;
08        for (int j = 0; j < i; j++)
09            if (a[j] < a[i]) f[i] = max(f[i], f[j] + 1);
10        lis = max(lis, f[i]);
11    }
12    int cur = 0, best = 0;               // 最大子段和:必须连续
13    for (int i = 0; i < 5; i++) {
14        cur += a[i];
15        if (cur < 0) cur = 0;
16        best = max(best, cur);
17    }
18    cout << lis << " " << best;
19    return 0;
20}

单选题:程序输出是?

(1 分)
拾壹

01 背包代码

7 QUESTIONS · 2 POINTS EACH
第 64 题 K1 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[5] = {0, 2, 3, 4, 5};          // 物品重量(1 下标)
05    int v[5] = {0, 3, 4, 5, 6};          // 物品价值
06    int C = 8, n = 4;
07    int f[10] = {0};                     // 不超过容量,全 0 初始化
08    for (int i = 1; i <= n; i++)
09        for (int j = C; j >= w[i]; j--)  // 容量倒序
10            f[j] = max(f[j], f[j - w[i]] + v[i]);
11    cout << f[C];
12    return 0;
13}

单选题:程序输出是?

(1 分)
第 65 题 K2 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[2] = {0, 2};                   // 只有一件物品:重 2 价值 3
05    int v[2] = {0, 3};
06    int C = 6, f[10] = {0};
07    for (int i = 1; i <= 1; i++)
08        for (int j = 0; j <= C; j++)     // 错误:容量正序循环
09            if (j >= w[i]) f[j] = max(f[j], f[j - w[i]] + v[i]);
10    cout << f[C];
11    return 0;
12}

单选题:程序输出是?(正确 01 背包结果应为 3

(1 分)
第 66 题 K3 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[4] = {0, 2, 3, 5};
05    int v[4] = {0, 3, 4, 7};
06    int C = 8, n = 3;
07    int f[10];
08    fill(f, f + 10, -1000000000);        // 恰好装满:其余不可达
09    f[0] = 0;
10    for (int i = 1; i <= n; i++)
11        for (int j = C; j >= w[i]; j--)
12            f[j] = max(f[j], f[j - w[i]] + v[i]);
13    cout << f[C];
14    return 0;
15}

单选题:程序输出是?

(1 分)
第 67 题 K4 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[5] = {0, 1, 1, 2, 3};          // 四件物品的重量
05    int C = 4, n = 4;
06    int f[10] = {0};
07    f[0] = 1;                            // 空集:1 种方案
08    for (int i = 1; i <= n; i++)
09        for (int j = C; j >= w[i]; j--)
10            f[j] += f[j - w[i]];         // 方案数用加法
11    cout << f[C];
12    return 0;
13}

单选题:程序输出是?

(1 分)
第 68 题 K5 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[4] = {0, 1, 3, 4};
05    int v[4] = {0, 2, 5, 7};
06    int C = 7, n = 3;
07    int f[10] = {0};
08    for (int i = 1; i <= n; i++)
09        for (int j = C; j >= w[i]; j--)
10            f[j] = max(f[j], f[j - w[i]] + v[i]);
11    cout << f[C];
12    return 0;
13}

单选题:程序输出是?

(1 分)
第 69 题 K6 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[3] = {0, 2, 3};
05    int v[3] = {0, 3, 4};
06    int C = 5, n = 2;
07    int f[3][10] = {0};                  // 二维表版
08    for (int i = 1; i <= n; i++)
09        for (int j = 0; j <= C; j++) {
10            f[i][j] = f[i - 1][j];       // 不选
11            if (j >= w[i]) f[i][j] = max(f[i][j], f[i - 1][j - w[i]] + v[i]);  // 选
12        }
13    cout << f[n][C];
14    return 0;
15}

单选题:程序输出是?

(1 分)
第 70 题 K7 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[3] = {0, 2, 4};
05    int v[3] = {0, 3, 5};
06    int C = 5, n = 2;
07    int f[10];
08    fill(f, f + 10, -1000000000);
09    f[0] = 0;
10    for (int i = 1; i <= n; i++)
11        for (int j = C; j >= w[i]; j--)
12            f[j] = max(f[j], f[j - w[i]] + v[i]);
13    cout << (f[C] < 0 ? -1 : f[C]);      // 恰好装满不可达 → -1
14    return 0;
15}

单选题:程序输出是?

(1 分)
拾贰

二维 DP 代码

6 QUESTIONS · 2 POINTS EACH
第 71 题 L1 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{1, 3, 1}, {1, 5, 1}, {4, 2, 1}};   // 3x3 矩阵
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 0; i < 3; i++)
08        for (int j = 0; j < 3; j++) {
09            if (i == 0 && j == 0) continue;
10            int best = -1e9;
11            if (i > 0) best = max(best, f[i - 1][j]);
12            if (j > 0) best = max(best, f[i][j - 1]);
13            f[i][j] = best + a[i][j];
14        }
15    cout << f[2][2];                 // 最大路径和
16    return 0;
17}

单选题:程序输出是?

(1 分)
第 72 题 L2 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{1, 3, 1}, {1, 5, 1}, {4, 2, 1}};
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int j = 1; j < 3; j++) f[0][j] = f[0][j - 1] + a[0][j];   // 第一行只能从左来
08    for (int j = 0; j < 3; j++) cout << f[0][j] << " ";
09    return 0;
10}

单选题:程序输出是?

(1 分)
第 73 题 L3 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int g[3][3] = {{0, 0, 0}, {0, 1, 0}, {0, 0, 0}};   // (1,1) 是障碍
05    int f[3][3] = {0};
06    f[0][0] = 1;
07    for (int i = 0; i < 3; i++)
08        for (int j = 0; j < 3; j++) {
09            if (g[i][j] == 1) { f[i][j] = 0; continue; }   // 障碍格不可达
10            if (i > 0) f[i][j] += f[i - 1][j];
11            if (j > 0) f[i][j] += f[i][j - 1];
12        }
13    cout << f[2][2];                 // 绕过障碍的路径数
14    return 0;
15}

单选题:程序输出是?

(1 分)
第 74 题 L4 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[2][2] = {{2, 3}, {5, 1}};
05    int f[2] = {0};                  // 滚动数组:只保留一行
06    f[0] = a[0][0];
07    f[1] = f[0] + a[0][1];           // 第 0 行
08    for (int j = 0; j < 2; j++) {    // 逐行滚动
09        if (j == 0) f[0] = f[0] + a[1][0];
10        else f[j] = max(f[j], f[j - 1]) + a[1][j];
11    }
12    cout << f[1];                    // 最大路径和
13    return 0;
14}

单选题:程序输出是?

(1 分)
第 75 题 L5 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{1, 3, 1}, {1, 5, 1}, {4, 2, 1}};
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 0; i < 3; i++)
08        for (int j = 0; j < 3; j++) {
09            if (i == 0 && j == 0) continue;
10            int best = -1e9;
11            if (i > 0) best = max(best, f[i - 1][j]);
12            if (j > 0) best = max(best, f[i][j - 1]);
13            f[i][j] = best + a[i][j];
14        }
15    for (int i = 0; i < 3; i++) {           // 打印整张 DP 表
16        for (int j = 0; j < 3; j++) cout << f[i][j] << " ";
17        cout << endl;
18    }
19    return 0;
20}

单选题:程序输出是?

(1 分)
第 76 题 L6 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{1, 3, 1}, {1, 5, 1}, {4, 2, 1}};
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 0; i < 3; i++)
08        for (int j = 0; j < 3; j++) {
09            if (i == 0 && j == 0) continue;
10            int best = -1e9;
11            if (i > 0) best = max(best, ______);   // 上方来源
12            if (j > 0) best = max(best, f[i][j - 1]);
13            f[i][j] = best + a[i][j];
14        }
15    cout << f[2][2];
16    return 0;
17}

单选题:横线处应填入?

(1 分)
拾叁

数字三角形代码

6 QUESTIONS · 2 POINTS EACH
第 77 题 M1 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{3, 0, 0}, {1, 5, 0}, {8, 6, 7}};
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 1; i < 3; i++)
08        for (int j = 0; j <= i; j++) {
09            f[i][j] = a[i][j];
10            if (j > 0) f[i][j] = max(f[i][j], f[i - 1][j - 1] + a[i][j]);
11            if (j < i) f[i][j] = max(f[i][j], f[i - 1][j] + a[i][j]);
12        }
13    cout << max({f[2][0], f[2][1], f[2][2]});
14    return 0;
15}

单选题:程序输出是?

(1 分)
第 78 题 M2 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[4][4] = {{5, 0, 0, 0}, {2, 8, 0, 0}, {9, 4, 7, 0}, {3, 6, 8, 2}};
05    int f[4][4] = {0};
06    for (int j = 0; j < 4; j++) f[3][j] = a[3][j];    // 最后一行
07    for (int i = 2; i >= 0; i--)                       // 自底向上
08        for (int j = 0; j <= i; j++)
09            f[i][j] = a[i][j] + max(f[i + 1][j], f[i + 1][j + 1]);
10    cout << f[0][0];                                   // 顶点最大值
11    return 0;
12}

单选题:程序输出是?

(1 分)
第 79 题 M3 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{3, 0, 0}, {1, 5, 0}, {8, 6, 7}};
05    int f[3][3] = {0}, from[3][3];       // from 记录上一行来源
06    f[0][0] = a[0][0];
07    for (int i = 1; i < 3; i++)
08        for (int j = 0; j <= i; j++) {
09            int best = -1, src = -1;
10            if (j > 0 && f[i - 1][j - 1] > best) { best = f[i - 1][j - 1]; src = j - 1; }
11            if (j < i && f[i - 1][j] > best) { best = f[i - 1][j]; src = j; }
12            f[i][j] = best + a[i][j];
13            from[i][j] = src;
14        }
15    int p = (f[2][0] >= f[2][1] ? (f[2][0] >= f[2][2] ? 0 : 2) : (f[2][1] >= f[2][2] ? 1 : 2));
16    vector<int> path;
17    for (int i = 2; i >= 0; i--) { path.push_back(a[i][p]); p = from[i][p]; }
18    for (int i = path.size() - 1; i >= 0; i--) cout << path[i] << " ";
19    return 0;
20}

单选题:程序输出是?

(1 分)
第 80 题 M4 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{3, 0, 0}, {1, 5, 0}, {8, 6, 7}};
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 1; i < 3; i++)
08        for (int j = 0; j <= i; j++) {
09            f[i][j] = INT_MAX;
10            if (j > 0) f[i][j] = min(f[i][j], f[i - 1][j - 1] + a[i][j]);
11            if (j < i) f[i][j] = min(f[i][j], f[i - 1][j] + a[i][j]);
12        }
13    cout << min({f[2][0], f[2][1], f[2][2]});    // 最小路径和
14    return 0;
15}

单选题:程序输出是?

(1 分)
第 81 题 M5 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{3, 0, 0}, {1, 5, 0}, {8, 6, 7}};
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 1; i < 3; i++)
08        for (int j = 0; j <= i; j++) {
09            f[i][j] = a[i][j];
10            if (j > 0) f[i][j] = max(f[i][j], f[i - 1][j - 1] + a[i][j]);
11            if (j < i) f[i][j] = max(f[i][j], f[i - 1][j] + a[i][j]);
12        }
13    for (int j = 0; j < 3; j++) cout << f[2][j] << " ";   // 打印最后一行
14    return 0;
15}

单选题:程序输出是?

(1 分)
第 82 题 M6 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{3, 0, 0}, {1, 5, 0}, {8, 6, 7}};
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 1; i < 3; i++)
08        for (int j = 0; j <= i; j++)
09            f[i][j] = ______ + a[i][j];   // 取上一行两个来源(注意越界)的最大值
10    cout << max({f[2][0], f[2][1], f[2][2]});
11    return 0;
12}

单选题:横线处应填入?

(1 分)
拾肆

完善程序

7 QUESTIONS · 2 POINTS EACH
第 83 题 N1 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int f[15];
05    f[1] = 1; f[2] = 2;
06    for (int i = 3; i <= 10; i++)
07        f[i] = ______;          // 爬楼梯转移
08    cout << f[10];
09    return 0;
10}

单选题:横线处应填入?

(1 分)
第 84 题 N2 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[8] = {3, 1, 4, 1, 5, 9, 2, 6};
05    int f[8], ans = 1;
06    for (int i = 0; i < 8; i++) {
07        f[i] = 1;
08        for (int j = 0; j < i; j++)
09            if (______) f[i] = max(f[i], f[j] + 1);   // LIS 转移条件
10        ans = max(ans, f[i]);
11    }
12    cout << ans;
13    return 0;
14}

单选题:横线处应填入?

(1 分)
第 85 题 N3 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[5] = {0, 2, 3, 4, 5};
05    int v[5] = {0, 3, 4, 5, 6};
06    int C = 8, n = 4, f[10] = {0};
07    for (int i = 1; i <= n; i++)
08        for (int j = ______; j >= w[i]; j--)   // 01 背包容量倒序
09            f[j] = max(f[j], f[j - w[i]] + v[i]);
10    cout << f[C];
11    return 0;
12}

单选题:横线处应填入?

(1 分)
第 86 题 N4 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{3, 0, 0}, {1, 5, 0}, {8, 6, 7}};
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 1; i < 3; i++)
08        for (int j = 0; j <= i; j++) {
09            f[i][j] = a[i][j];
10            if (j > 0) f[i][j] = max(f[i][j], ______);   // 左上来源
11            if (j < i) f[i][j] = max(f[i][j], f[i - 1][j] + a[i][j]);   // 正上来源
12        }
13    cout << max({f[2][0], f[2][1], f[2][2]});
14    return 0;
15}

单选题:横线处应填入?

(1 分)
第 87 题 N5 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{1, 3, 1}, {1, 5, 1}, {4, 2, 1}};
05    int f[3][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 0; i < 3; i++)
08        for (int j = 0; j < 3; j++) {
09            if (i == 0 && j == 0) continue;
10            int best = -1e9;
11            if (i > 0) best = max(best, f[i - 1][j]);
12            if (j > 0) best = max(best, ______);   // 左方来源
13            f[i][j] = best + a[i][j];
14        }
15    cout << f[2][2];
16    return 0;
17}

单选题:横线处应填入?

(1 分)
第 88 题 N6 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[4] = {0, 2, 3, 5};
05    int v[4] = {0, 3, 4, 7};
06    int C = 8, n = 3;
07    int f[10];
08    ______;                // 恰好装满:只有 f[0] 合法
09    f[0] = 0;
10    for (int i = 1; i <= n; i++)
11        for (int j = C; j >= w[i]; j--)
12            f[j] = max(f[j], f[j - w[i]] + v[i]);
13    cout << f[C];
14    return 0;
15}

单选题:横线处应填入?

(1 分)
第 89 题 N7 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int f[3][3] = {0};
05    f[0][0] = 1;
06    for (int i = 0; i < 3; i++)
07        for (int j = 0; j < 3; j++) {
08            if (i > 0) f[i][j] += ______;   // 从上方来
09            if (j > 0) f[i][j] += f[i][j - 1];   // 从左方来
10        }
11    cout << f[2][2];
12    return 0;
13}

单选题:横线处应填入?

(1 分)
拾伍

代码综合应用

5 QUESTIONS · 2 POINTS EACH
第 90 题 O1 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[4] = {0, 1, 2, 3};             // 重量
05    int v[4] = {0, 2, 3, 5};             // 价值
06    int C = 3, n = 3;
07    int f[10] = {0}, g[10] = {0};        // f:价值,g:方案数
08    g[0] = 1;
09    for (int i = 1; i <= n; i++)
10        for (int j = C; j >= w[i]; j--) {
11            if (f[j - w[i]] + v[i] > f[j]) { f[j] = f[j - w[i]] + v[i]; g[j] = g[j - w[i]]; }
12            else if (f[j - w[i]] + v[i] == f[j]) g[j] += g[j - w[i]];
13        }
14    cout << g[C];                        // 最优价值对应的方案数
15    return 0;
16}

单选题:程序输出是?

(1 分)
第 91 题 O2 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[3][3] = {{1, 0, 0}, {-2, 3, 0}, {4, -5, 6}};
05    int f[3][3];
06    for (int i = 0; i < 3; i++)
07        for (int j = 0; j < 3; j++) f[i][j] = INT_MIN;   // 含负数,初值要极小
08    f[0][0] = a[0][0];
09    for (int i = 1; i < 3; i++)
10        for (int j = 0; j <= i; j++) {
11            int best = INT_MIN;
12            if (j > 0) best = max(best, f[i - 1][j - 1]);
13            if (j < i) best = max(best, f[i - 1][j]);
14            f[i][j] = best + a[i][j];
15        }
16    cout << max({f[2][0], f[2][1], f[2][2]});
17    return 0;
18}

单选题:程序输出是?

(1 分)
第 92 题 O3 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[4] = {1, 3, 2, 4};
05    int f[4], g[4], ans = 1, ways = 0;
06    for (int i = 0; i < 4; i++) {
07        f[i] = 1; g[i] = 1;
08        for (int j = 0; j < i; j++)
09            if (a[j] < a[i]) {
10                if (f[j] + 1 > f[i]) { f[i] = f[j] + 1; g[i] = g[j]; }
11                else if (f[j] + 1 == f[i]) g[i] += g[j];
12            }
13        if (f[i] > ans) { ans = f[i]; ways = g[i]; }
14        else if (f[i] == ans) ways += g[i];
15    }
16    cout << ans << " " << ways;          // 最长长度与方案数
17    return 0;
18}

单选题:程序输出是?

(1 分)
第 93 题 O4 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[2][3] = {{1, 2, 3}, {4, 5, 6}};   // 2x3 矩阵
05    int f[2][3] = {0};
06    f[0][0] = a[0][0];
07    for (int i = 0; i < 2; i++)
08        for (int j = 0; j < 3; j++) {
09            if (i == 0 && j == 0) continue;
10            int best = -1e9;
11            if (i > 0) best = max(best, f[i - 1][j]);
12            if (j > 0) best = max(best, f[i][j - 1]);
13            f[i][j] = best + a[i][j];
14        }
15    cout << f[1][2];                 // 最大路径和
16    return 0;
17}

单选题:程序输出是?

(1 分)
第 94 题 O5 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[4] = {0, 1, 2, 3};
05    int v[4] = {0, 2, 3, 5};
06    int C = 4, n = 3;
07    int f[10];
08    fill(f, f + 10, -1000000000);
09    f[0] = 0;
10    for (int i = 1; i <= n; i++)
11        for (int j = C; j >= w[i]; j--)
12            f[j] = max(f[j], f[j - w[i]] + v[i]);
13    cout << f[C];                        // 恰好装满 C 的最大价值
14    return 0;
15}

单选题:程序输出是?

(1 分)
拾陆

代码易错

6 QUESTIONS · 2 POINTS EACH
第 95 题 P1 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[3] = {0, 2, 3};
05    int v[3] = {0, 3, 4};
06    int C = 8, f[10] = {0};
07    for (int i = 1; i <= 2; i++)
08        for (int j = 0; j <= C; j++)     // 错误:容量正序
09            if (j >= w[i]) f[j] = max(f[j], f[j - w[i]] + v[i]);
10    cout << f[C];                        // 正确 01 背包应为 7
11    return 0;
12}

单选题:程序输出是?

(1 分)
第 96 题 P2 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[3] = {0, 2, 4};
05    int v[3] = {0, 3, 5};
06    int C = 5, f[10] = {0};              // 错误:恰好装满却全 0 初始化
07    for (int i = 1; i <= 2; i++)
08        for (int j = C; j >= w[i]; j--)
09            f[j] = max(f[j], f[j - w[i]] + v[i]);
10    cout << f[C];                        // 恰好 5 其实不可达(正确应输出 -1)
11    return 0;
12}

单选题:程序输出是?

(1 分)
第 97 题 P3 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int w[2] = {0, 2};
05    int v[2] = {0, 3};
06    int C = 4, f[10] = {0};
07    for (int i = 1; i <= 1; i++)
08        for (int j = w[i]; j <= C; j++)
09            f[j] = f[j - w[i]] + v[i];   // 错误:漏了"不选"(f[j] 被覆盖)
10    cout << f[C];                        // 正确结果应为 3
11    return 0;
12}

单选题:程序输出是?

(1 分)
第 98 题 P4 未作答

单选题:01 背包滚动数组版把内层写成 for (int j = 0; j <= C; j++) f[j] = max(f[j], f[j - w] + v);(没有 j >= w 判断),会发生什么?

(1 分)
第 99 题 P5 未作答

01#include <bits/stdc++.h>
02using namespace std;
03int main() {
04    int a[4] = {1, 2, 1, 3};
05    int f[4];
06    f[0] = 1;
07    for (int i = 1; i < 4; i++)
08        f[i] = (a[i] > a[i - 1]) ? f[i - 1] + 1 : 1;   // 错误:只统计"连续"上升段
09    cout << f[3];                        // 正确 LIS(不要求连续)应为 3
10    return 0;
11}

单选题:程序输出是?

(1 分)
第 100 题 P6 未作答

判断题:以下结论全部正确——"滚动数组 01 背包容量必须倒序;LIS 的答案是 max(f[1..n]);二维 DP 边界行列要特判;恰好装满背包初始化只有 f[0] = 0 合法"。

(1 分)