因此,我正在尝试为rod cutting problem的修改版本编写代码。该链接很好地说明了问题。但是,我想修改代码以不仅实际返回解决方案(即哪些割线可提供最佳解决方案),而且还将割线数限制为最大k。
为证明概念,我正在尝试创建一种算法来实现这一目标。以下是到目前为止的内容,我认为它成功返回了实际的解决方案,但是,我不知道如何将最大值限制为k。
let r[0..n] be a new array
r[0] = 0
for j = 1 to n
q = -1
for i = 1 to j
for k = 0 to n-1
q = Math.max(q[n][k], p[i] + q[n-i-1][k-1]);
r[j] = q
return r[n]
请不要在您的答案中提供实际的代码,我想自己实现,我只需要调整我的算法以提供正确的解决方案即可。
更新1:通过向数组添加第二维,我已经能够找到最多k个切口的最佳解决方案。如上面的代码所示。
答案 0 :(得分:0)
正如您所说,您已经拥有了最佳的解决方案,此答案仅包括如何追溯确切的解决方案(在每个步骤进行切割)。
为此,您只需要一个2维数组(例如visit[n][k]
)来存储制作的切割,该切割可获得q[n][k]
的最大解。在伪代码和递归关系方面,如下所示。
for each value of i:
q[n][k] = q[n][k-1]
visit[n][k] = -1
if q[n][k] < p[i] + q[n-i-1][k-1]:
q[n][k] = p[i] + q[n-i-1][k-1]
visit[n][k] = i
visit[n][k] = -1
。n
处切割长度length=i+1
的杆,即。我们可以通过切割获得更好的价格,我们将相应的切割存储在另一个二维数组中。使用此二维数组(visit[n][k]
)来追溯精确的切割,您可以使用以下伪代码(我故意避免使用代码,因为您提到您不需要它)。
cuts = []
while k > 0:
i = visit[n][k]
if i != -1
// If there is a cut
cuts.push(i + 1)
n = n - i - 1
k = k - 1
k
迭代到0
。visit[n][k]
不是-1
时,即最好在某处切割,我们在切割后重新分配n
,即。 n = n-i-1并将结果cut
存储在数组cuts
中。cuts
将包含导致最佳解决方案的精确切割。请注意,就递归关系中使用的变量而言,问题中存在的伪代码有些不正确。 q
用于存储DP 2-d数组和整数-1
。 j
根本没有在自下而上的DP中使用,而是由常量n
代替。 q[j][k]
未初始化。但是,总体思路是正确的。