带加权边缘的 1/0 背包变化
Posted
技术标签:
【中文标题】带加权边缘的 1/0 背包变化【英文标题】:1/0 Knapsack Variation with Weighted Edges 【发布时间】:2015-01-13 17:39:37 【问题描述】:我目前正在调查一个路线问题(在不超过最长旅行时间的情况下找到我想去的地方的子集 [每个都有一定的分数]),并提出了 1/0 背包问题的变体:似乎解决了我原来的问题。
根据***,1/0 背包被描述为:
给定一组项目,每个项目都有一个质量和一个值,确定要包含在集合中的每个项目的数量,以便总重量小于或等于给定限制,并且总值与可能。
因此,对于每个项目,都有一个固定的重量(质量),可以在尝试解决问题时轻松使用,例如使用动态规划。
但是,如果特定物品的重量取决于包的先前内容怎么办?换句话说(并且以更一般的方式):让我们考虑以下完整的图表:
每个节点 (A,B,C,D,E) 代表我可能想要放入背包的物品。让我们假设每个节点也有一个特定的 value 分配给它(图中省略)。我仍然希望有一个最佳背包,因此是具有最高分数的节点的子集,但是这次权重(或将特定节点添加到我当前的背包的成本)没有分配给节点本身,而是分配给边缘导致它。
这意味着添加节点的成本取决于背包的先前内容(例如,通过使用任何已包含节点中成本最低的边)。例如,如果我当前的背包由 A,C 组成,则添加 B 的成本为 2(取 A->B 或 C->B)。如果我当前的背包由 D,E 组成,则添加 B 的成本改为 3。
不幸的是,我真的想不出一个好的算法来解决这个问题。 经典的背包 DP 方法在这里实际上并不适用,因为您可以轻松地构造它不返回最佳解决方案的情况。例如,如果您开始使用“错误”节点构建您的背包,则添加一个非常好的节点(应该包含在最佳解决方案中但尝试很晚)的成本可能会超过容量。
我是否采取了完全错误的方法来解决问题?你认为有更好的算法来解决这个问题吗?
【问题讨论】:
【参考方案1】:首先,这个问题是 NP 难的。这是从加权完整图中的最短哈密顿路径到此路径的简化。给定一个图,我们可以将所有节点的值分配为 1,然后对答案运行二进制搜索。如果这个问题有多项式解决方案,它可以判断是否存在包含所有顶点且不长于给定值的路径。因此,我们将能够在多项式时间内解决最短哈密顿路径问题。在实践中,这意味着没有人知道您的问题的有效正确多项式解决方案。
现在有两种方法:
如果顶点的数量相当少(大约 20 个),您可以使用动态规划来获得精确的解决方案。状态为(mask, last_vertex)
。该值是我们需要访问mask
中的所有顶点并停止在last_vertex
中的最短时间。该方案的时间复杂度为O(2^n * n^2)
。
如果顶点的数量大得多,你可以找到一个近似的解决方案。有很多方法可以做到这一点:启发式、不同的贪心算法、局部优化的随机抽样等等。
【讨论】:
非常感谢您的有用回答。以上是关于带加权边缘的 1/0 背包变化的主要内容,如果未能解决你的问题,请参考以下文章
使用背包解决硬币变化。参考:另一个背包 Hackerrank CodeAgon