AcWing算法基础课---第五讲动态规划
背包问题
-
01背包
(1). 二维dp#include<iostream> using namespace std; const int N = 1010; int m, n; int V[N], W[N]; int f[N][N]; //f[i][j]表示从i个物品中选,容量不超过j的最大价值 int main() { cin >> n >> m; for (int i = 1; i <= n; i ++) cin >> V[i] >> W[i]; for (int i = 1; i <= n; i ++) { for (int j = 0; j <= m; j ++) { f[i][j] = f[i - 1][j]; //不包含i肯定存在 if (j >= V[i]) f[i][j] = max(f[i][j], f[i - 1][j - V[i]] + W[i]); //包含i可能不存在 } } cout << f[n][m]; return 0; }
(2). 压缩为一维dp
#include<iostream> using namespace std; const int N = 1010; int m, n; int V[N], W[N]; int f[N]; //f[i][j]表示从i个物品中选,容量不超过j的最大价值 int main() { cin >> n >> m; for (int i = 1; i <= n; i ++) cin >> V[i] >> W[i]; for (int i = 1; i <= n; i ++) for (int j = m; j >= V[i]; j --) { f[j] = max(f[j], f[j - V[i]] + W[i]); //包含i可能不存在 } cout << f[m]; return 0; }
-
完全背包
(1). 二维#include<iostream> using namespace std; const int N = 1010; int n, m; int v[N], w[N]; int f[N][N]; int main() { cin >> n >> m; for (int i = 1; i <= n; i ++) cin >> v[i] >> w[i]; for (int i = 1; i <= n; i ++) for (int j = 0; j <= m; j ++) { f[i][j] = f[i - 1][j]; if (j >= v[i]) f[i][j] = max(f[i][j], f[i][j - v[i]] + w[i]); } cout << f[n][m]; return 0; }
(2). 一维
#include<iostream> using namespace std; const int N = 1010; int n, m; int v[N], w[N]; int f[N]; int main() { cin >> n >> m; for (int i = 1; i <= n; i ++) cin >> v[i] >> w[i]; for (int i = 1; i <= n; i ++) for (int j = v[i]; j <= m; j ++) f[j] = max(f[j], f[j - v[i]] + w[i]); cout << f[m]; return 0; }
-
多重背包
#include<iostream> using namespace std; const int N = 10010; int n, m; int v[N], w[N]; int f[N]; int main() { cin >> n >> m; int cnt = 0; for (int i = 1; i <= n; i ++) { int a, b, s; cin >> a >> b >> s; int k = 1; //打包 while (k <= s) { cnt ++; v[cnt] = a * k; w[cnt] = b * k; s -= k; k *= 2; } if (s > 0) { cnt ++; v[cnt] = a * s; w[cnt] = b * s; } } n = cnt; for (int i = 1; i <= n; i ++) for (int j = m; j >= v[i]; j --) f[j] = max(f[j], f[j - v[i]] + w[i]); cout << f[m]; return 0; }
-
分组背包
#include <iostream> using namespace std; const int N = 110; int n, m; int v[N][N], w[N][N], s[N], f[N]; int main() { cin >> n >> m; for (int i = 1; i <= n; i ++) { cin >> s[i]; for (int j = 0; j < s[i]; j ++) cin >> v[i][j] >> w[i][j]; } for (int i = 1; i <= n; i ++) for (int j = m; j >= 0; j --) for (int k = 0; k < s[i]; k ++) if (v[i][k] <= j) //判断是否能装下!!! f[j] = max(f[j], f[j - v[i][k]] + w[i][k]); cout << f[m]; return 0; }
分类:
AcWing算法基础课
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现