为此使用PHP。
从给定的一组物品中,每个物品都有自己的重量,我需要自动计算将物品包装成100磅包装的最有效方法(最大包装重量100磅是静态的,但可以在将来改变)。单个包装不能超过指定的最大值。
例如,我有5个项目 - 总重量为254磅:
人们会认为254磅需要3 x 100磅的包装。这个例子有意地证明了情况并非总是如此。某些项目配置无法很好地协同工作。这个例子需要4 x 100 lbs的最佳配置包。
项目数量和权重是完全可变的,任何单个项目都不会超过100磅。
实现这一目标的最佳方式是什么?
答案 0 :(得分:8)
您所描述的问题称为Bin Packing Problem。没有人知道解决它的最佳方法。如果他们这样做,他们将能够证明P=NP或P!= NP - 计算中一个重要的开放性问题。
维基百科页面包括对一些示例算法的引用 - 第一拟合算法,最佳拟合递减,第一拟合递减。通常,解决此问题的一种快速方法是不尝试找到最佳解决方案,而是找到一个好的近似值。 “减少”指的是首先包装最大,最笨拙的元素,然后用最后的小元素填充间隙是一个好主意。这实际上类似于大多数人通常如何解决这个问题。
对于您在示例中给出的问题的大小,通过检查所有可能的排列来找到最佳解决方案很简单,但显然对于较大的示例而言效率不高。
答案 1 :(得分:1)
问题实际上与此处讨论的相同:
Convert function from recursion to iteration
盲搜索方法是应用每个组合的组合,这将创建一个N阶的算法!如果你只有少量的项目不是一个大问题(5个项目只提供120个组合搜索 - 但10需要超过360万)
根据我的帖子,请参阅
http://en.wikipedia.org/wiki/Travelling_salesman_problem
有关非详尽算法的描述。
下进行。
答案 2 :(得分:0)
对于那些感兴趣的人,这是我为解决我的问题所写的代码:
//Loop thru cart items - adding weights to packages
foreach((array)$this->cart_items as $cart_item) {
for ($i = 0; $i < $cart_item->quantity; $i++) {
$itemWeight = $cart_item->weight; //Get current item weight
$currWeight += $itemWeight; //Add item weight to active package
if ($currWeight > 100){ //Max weight reached for active package
$currWeight -= $itemWeight; //Remove item from current package, too heavy
$loopPack = 0;
$itemUsed = false;
//Check if an existing package can take the item
while (($loopPack != $packageCount) or ($itemUsed = false)) {
if ($packages[$loopPack] + $itemWeight < 100) {
$packages[$loopPack] += $itemWeight;
$itemUsed = true;
}
$loopPack++;
}
//if the item didn't fit in an existing package, create a new package for it
if ($itemUsed == false) {
$packageCount++;
$packages[$packageCount-1] = $currWeight;
$currWeight = $cart_item->weight; //Put unused item back in active package
}
}
}
}
//The remainder becomes a package
$packageCount++;
$packages[$packageCount-1] = $currWeight;
print_r($packages);