复杂动态规划,如何定义重叠子问题

Complex dynamic programming, how to define overlapping subproblems

生产者想雇用新工人。每一位新员工都会为公司带来额外的价值。同一个部门的每个下一个工人带来的价值都与他之前的一个工人相等或更少。例如

 Division #1: Division #2: ...
 0: 0         0
 1: 30        35
 2: 55        65
 3: 78        90
 4: 97        110
 5: 115       .
 6: 131       .
 7: 144       .
 8: 154
 9: 160
10: 163

生产商希望通过尽可能少的新员工为其公司增加 250 美元的额外价值。他应该如何在部门之间分配新工人。

编辑:正如评论所要求的:如果您向 Division #1 添加 0 个工人,您的公司价值将增加 0 美元。


我需要知道如何定义子问题。

我无法接受这样一个事实,即在为下一个工人添加每个工人后 table 发生了变化。即更改了 worker 所在的部门列。所以,我不能说我有同样的问题,只是获得的新价值更少。

令 v(i, j) 为 j 名新员工为第 i 个部门带来的美元价值。这基本上是你问题的转置 table。

对于 n 个部门,您正在寻找一个自然数序列 w1, ..., wn 使得 SUM (i = 1..n, wi) 是最小值并且 SUM(i = 1..n, v(i, wi) ) ≥ 250.

主要的观察是,如果你已经将 wi 分配给 wk 一些 k,你不需要知道解决将 wk+1 分配给 wn 的剩余子问题的确切分配。你只需要知道你已经分配了多少工人以及你已经增加了多少价值。您基本上可以将 wi 到 wk (呈指数级增长)的可能赋值的 space 减少到两个整数值代表您关心的所有信息。事实上,我们甚至不关心 (a = worker 数量,b = 值) 的所有组合,只关心那些没有被其他对 (c, d) 取代的组合,其中 c <= d 且 d >= b ).

你可以定义f(i, x)为w1, .., wi的最小工人总数使得附加值≥x.

显然我们有 f(0, 0) = 0 和 f(0, x) = ∞ for x > 0。无穷大值表示不可能实现这种情况。

我们也可以证明递归

f(i + 1, x) = MIN(w = 0 到 ∞, f(i, max(0, x - v(i + 1, w))))

这导致了一个简单的 DP 算法来计算 f。

您感兴趣的函数值为f(n, 250)。