背包
01背包
设 dp[i][j] 表示在前 i 个物品中已经选好了最佳方案,并且容量不超过 j 时,所能获取的最大价值。
(对于任意一个 dp[i][j] ,已知 dp[1 ~ i - 1][1 ~ j - 1])
对于 i 物品,如果选择不装入,则有 dp[i][j] = dp[i - 1][j]。
如果选择装入,则有 dp[i][j] = dp[i - 1][j - v[i]] + w[i]。
两者取最大,则有 dp[i][j] = max(dp[i - 1][j], dp[i][j] = dp[i - 1][j - v[i]] + w[i])。
初始化 dp[0][0 ~ V] = 0,答案为 dp[T][V]。
例题:
P1048 [NOIP2005 普及组] 采药
AC
完全背包
状态设计同 01 背包
对于 i 物品,如果选择不装入,则有 dp[i][j] = dp[i - 1][j]。
如果选择装入,则有 dp[i][j] = dp[i][j - v[i]] + w[i]。
两者取最大,则有 dp[i][j] = max(dp[i - 1][j], dp[i][j] = dp[i][j - v[i]] + w[i])。
初始化 dp[0][0 ~ V] = 0,答案为 dp[T][V]。
例题:
P1616 疯狂的采药
AC(滚动数组优化)
AC(一维优化)
优化
滚动数组优化
对于状态转移方程 dp[i][j] = max(dp[i - 1][j], dp[i][j] = dp[i - 1][j - v[i]] + w[i])。
可以发现只会使用到 dp[i] 和 dp[i - 1]。
即可以将 dp[MAXM][MAXN] 优化为 dp[2][MAXN]。
一维
对于上述滚动数组优化,可以注意到 dp[now][j] 的影响因素只有 dp[last][j] 和 dp[last][j - v[i]] + w[i]。
所以只要更改 j 的枚举方向,便可以再次优化一维。