2022 上升点列 · 方案二 二维动态规划
状态加上补了几个点,剩的点加在末尾
正文
// CSP-J 2022 复赛 T4 · 上升点列(方案二 · 满分)
// 原题:https://oj.yecheng.tv/p/CSPJ2022D
//
// 方案二 · 二维 DP:把「补了几个点」也记进状态
// 两个核心观察:
// 1. 从点 h 走到点 i(h 在 i 的左下方),中间要补的整点个数是固定的:
// t = (x_i - x_h) + (y_i - y_h) - 1
// 补上这 t 个点后,这一段一共贡献 t + 1 个新点。
// 2. 补点不一定要全花在中间 —— 往序列末尾继续加整点同样能拉长序列,
// 而且想加多少就加多少。所以 k 个补点一定会被全部用光,
// 答案 = 「链里用到的给定点个数」 + k。
// 于是定义 dp[i][j] = 以第 i 个点结尾、中间一共补了 j 个点时,
// 链里最多能包含多少个给定点。转移就是枚举前一个点 h:
// dp[i][j] = max(dp[h][j - t] + 1),要求 j >= t 且 h 在 i 的左下方。
// 答案 = max(dp[i][j]) + k,其中 j <= k。
// 复杂度 O(n^2 * k),n = 500、k = 100,约 2.5e7,稳过。
#include <bits/stdc++.h>
using namespace std;
struct Point {
long long x, y;
};
bool cmpPoint(const Point& A, const Point& B) {
if (A.x != B.x) return A.x < B.x;
return A.y < B.y;
}
int dp[505][105];
int main() {
freopen("point.in", "r", stdin);
freopen("point.out", "w", stdout);
int n, k;
cin >> n >> k;
vector<Point> p(n);
for (int i = 0; i < n; i++) cin >> p[i].x >> p[i].y;
sort(p.begin(), p.end(), cmpPoint);
int best = 1;
for (int i = 0; i < n; i++) {
for (int j = 0; j <= k; j++) {
dp[i][j] = 1; // 只有自己一个给定点
for (int h = 0; h < i; h++) {
if (p[h].x > p[i].x || p[h].y > p[i].y) continue;
long long t = (p[i].x - p[h].x) + (p[i].y - p[h].y) - 1;
if (t > j) continue; // 补点不够,接不上
dp[i][j] = max(dp[i][j], dp[h][j - (int)t] + 1);
}
best = max(best, dp[i][j]);
}
}
cout << best + k << "\n"; // 剩下的补点全加在末尾
return 0;
}
CSP-J 标程 · 复赛真题的其它内容
- 2019 数字游戏 · 方案一 逐字符统计
- 2019 数字游戏 · 方案二 二进制位运算
- 2020 优秀的拆分 · 方案一 贪心从大到小减
- 2020 优秀的拆分 · 方案二 直接看二进制位
- 2021 分糖果 · 方案一 枚举每个 k
- 2021 分糖果 · 方案二 看余数在哪一段
- 2022 乘方 · 方案一 边乘边判断
- 2022 乘方 · 方案二 快速幂加封顶
- 2023 小苹果 · 方案一 照规则真模拟
- 2023 小苹果 · 方案二 只盯住两个数字
- 2024 扑克牌 · 方案一 用集合去重
- 2024 扑克牌 · 方案二 二维布尔表
- 2025 拼数 · 方案一 收集后降序排序
- 2025 拼数 · 方案二 桶计数
- 2019 公交换乘 · 方案一 暴力匹配
- 2019 公交换乘 · 方案二 时间窗口优化
- 2020 直播获奖 · 方案一 每轮排序
- 2020 直播获奖 · 方案二 桶计数
- 2021 插入排序 · 方案一 每次真排一遍
- 2021 插入排序 · 方案二 增量维护有序表
- 2022 解密 · 方案一 二分求整数平方根
- 2022 解密 · 方案二 先估后校开方
- 2023 公路 · 方案一 朴素贪心
- 2023 公路 · 方案二 单调栈预处理
- 2024 地图探险 · 方案一 四方向分支写
- 2024 地图探险 · 方案二 方向数组
- 2025 座位 · 方案一 把座位表填出来
- 2025 座位 · 方案二 直接算排名
- 2019 纪念品 · 方案一 逐天完全背包
- 2019 纪念品 · 方案二 砍掉不赚钱物品
- 2020 表达式 · 方案一 每次重算后缀式
- 2020 表达式 · 方案二 建树加关键性传播
- 2021 网络连接 · 方案一 手写解析
- 2021 网络连接 · 方案二 读入后回拼校验
- 2022 逻辑表达式 · 方案一 递归分治
- 2022 逻辑表达式 · 方案二 递归下降
- 2023 一元二次方程 · 方案一 照公式逐步写
- 2023 一元二次方程 · 方案二 拆成小函数
- 2024 小木棍 · 方案一 先定位数再贪心
- 2024 小木棍 · 方案二 预处理最小数字表
- 2025 异或和 · 方案一 贪心能接就接
- 2025 异或和 · 方案二 动态规划加值域数组
- 2019 加工零件 · 方案一 递归加记忆化
- 2019 加工零件 · 方案二 奇偶最短路
- 2020 方格取数 · 方案一 深搜回溯
- 2020 方格取数 · 方案二 按列动态规划
- 2021 小熊的果篮 · 方案一 每轮扫一遍
- 2021 小熊的果篮 · 方案二 链表加有序集合
- 2022 上升点列 · 方案一 先只考虑不加点
- 2023 旅游巴士 · 方案一 分层图加优先队列
- 2023 旅游巴士 · 方案二 状态压成一维
- 2024 接龙 · 方案一 按定义广搜
- 2024 接龙 · 方案二 滑动窗口逐轮推进
- 2025 多边形 · 方案一 枚举所有子集
- 2025 多边形 · 方案二 排序加计数 DP