【拼多多】20250309笔试真题第3题记录
因为之前坐过二维dp(后来才知道这其实叫序列dp)的题,所以看到这个题还是有一些思路的,但是这个题的关键点在于初始化,一定要初始化非法状态,不能一上来就初始化全为0
这题还是有收获的
不过还是那句话,菜就多练
#include <bits/stdc++.h>
using namespace std;
int main(int argc, char const* argv[]) {
int n = 0, m = 0;
cin >> n >> m;
int a[n] = {0};
for (int i = 0; i < n; i++) {
cin >> a[i];
}
// 在 m 分钟内读完 n 页, 每一分钟最多读 2 页
if (n > 2 * m) {
cout << "-1";
return 0;
}
double dp[n + 1][m + 1];
// dp[i][j]表示第i分钟读了j页能获取到最大知识量
// 只要在 m 分钟内读完 n 页就可以
// 最大知识量显然为max({dp[1][n], dp[2][n], dp[3][n], ... dp[m][n]})
// 关键的初始化
// dp[i][j] = -1 表示不合法状态, 比如说 1 分钟最多读完第 2 页, 不可能读完第 3 页
for (int i = 1; i <= m; i++) {
for (int j = 1; j <=n; j++) {
dp[i][j] = -1.0;
}
}
// 第 0 分钟读完 0 页获得的知识量为 0.0
dp[0][0] = 0.0;
for (int i = 1; i <= m; i++) {
for (int j = 1; j <= n; j++) {
// 注意这里一开始的 i = j = 1
// 也就是dp[1][1] 表示第 1 分钟读完第 1 页能获得的最大知识量
// 只读一页且状态合法
if (dp[i - 1][j - 1] > -1) {
dp[i][j] = max(dp[i][j], dp[i - 1][j - 1] + a[j - 1]);
}
// 读 2 页且状态合法
else if (j > 1 && dp[i - 1][j - 2] > -1) {
dp[i][j] = max(dp[i][j], dp[i - 1][j - 2] + (a[j - 1] + a[j - 2]) / 2);
}
}
}
double ans = 0.0;
for (int i = 1; i <= m; i++) {
ans = max(ans, dp[i][n]);
}
cout << fixed << setprecision(1) << ans;
system("pause");
return 0;
}
查看12道真题和解析
美的集团公司福利 835人发布