| Run ID | 作者 | 问题 | 语言 | 测评结果 | 时间 | 内存 | 代码长度 | 提交时间 |
|---|---|---|---|---|---|---|---|---|
| 91912 | sh25_shenpy | 磁带最大利用率问题 | C++ | 无测评数据 | 0 MS | 0 KB | 1916 | 2026-06-19 15:40:48 |
#include <iostream> #include <vector> #include <algorithm> #include <cstring> using namespace std; const int MAXN = 105; const int MAXL = 10005; int n, L; int l[MAXN]; // dp[i][j] = 选i个程序,总长不超过j的最大长度 int dp[MAXN][MAXL]; bool take[MAXN][MAXL]; // 记录是否选第k个 int main() { cin >> n >> L; for (int i = 1; i <= n; ++i) cin >> l[i]; // 第一步:贪心求最多能存多少个 m vector<int> v(l + 1, l + n + 1); sort(v.begin(), v.end()); int sum = 0, m = 0; for (int x : v) { if (sum + x <= L) { sum += x; m++; } else break; } // 第二步:01背包,恰好选 m 个,总长度 <= L,最大和 memset(dp, -0x3f, sizeof(dp)); dp[0][0] = 0; for (int k = 1; k <= n; ++k) { int len = l[k]; for (int i = m; i >= 1; --i) { for (int j = L; j >= len; --j) { if (dp[i - 1][j - len] + len > dp[i][j]) { dp[i][j] = dp[i - 1][j - len] + len; take[i][j] = true; } } } } // 找最大利用率 int max_use = 0; int j_best = 0; for (int j = 0; j <= L; ++j) { if (dp[m][j] > max_use) { max_use = dp[m][j]; j_best = j; } } // 回溯选了哪些 vector<int> res; int i = m, j = j_best; for (int k = n; k >= 1 && i > 0; --k) { if (take[i][j]) { res.push_back(l[k]); j -= l[k]; i--; } } reverse(res.begin(), res.end()); // 输出 cout << m << " " << max_use << endl; for (int x : res) cout << x << " "; cout << endl; return 0; }