Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/algorithm/11.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 在背包里找到物品_C#_Algorithm_Recursion_Knapsack Problem - Fatal编程技术网

C# 在背包里找到物品

C# 在背包里找到物品,c#,algorithm,recursion,knapsack-problem,C#,Algorithm,Recursion,Knapsack Problem,我想用C#递归地解决背包问题。这是我的代码: public int f(int n, int remain) { if (n < 0) return 0; if (w[n] > remain) { // Thread.VolatileWrite(ref check[n], 0); check[n] = 0; return f(n - 1, remain); } else {

我想用C#递归地解决背包问题。这是我的代码:

public  int f(int n, int remain)
{
    if (n < 0) return 0;
    if (w[n] > remain)
    {
        //    Thread.VolatileWrite(ref   check[n], 0);
        check[n] = 0;
        return f(n - 1, remain);
    }
    else
    {
        int a = f(n - 1, remain);
        int b = p[n] + f(n - 1, remain - w[n]);
        if (a >= b)
        {
            //   Thread.VolatileWrite(ref   check[n], 0);
            check[n] = 0;
            return a;
        }
        else
        {
            //  Thread.VolatileWrite(ref   check[n], 1);
            check[n] = 1;
            return b;
        }
    }
}
public int f(int n,int剩余)
{
如果(n<0)返回0;
如果(w[n]>保留)
{
//线程.VolatileWrite(参考检查[n],0);
检查[n]=0;
返回f(n-1,剩余);
}
其他的
{
int a=f(n-1,剩余);
intb=p[n]+f(n-1,剩余-w[n]);
如果(a>=b)
{
//线程.VolatileWrite(参考检查[n],0);
检查[n]=0;
返回a;
}
其他的
{
//线程写入(参考检查[n],1);
检查[n]=1;
返回b;
}
}
}
w
是一个包含权重的数组,
p
是一个包含价格的数组
n
是项目数,
剩余
是最大重量


我的问题是
检查
数组。我使用这个数组来存储将要放入包中的项目,但它并不总是有效,有时解决方案是正确的,有时则不是。我什么都试过了,但还是想不出来。如何解决此问题?

检查数组的用法是错误的,因为它指示最后一次赋值,并且不必是所选的赋值

下面是一个反例,解释了为什么它不起作用

假设:

weights = [1,2]
values = [2,1]
w = 2
现在,让我们看看会发生什么:

f(1,2):
   f(0,2):
       f(-1,2)  = 0
       a = 0
       f(-1,1) = 0
       b = 2 + 0 = 2
       b>a -> check[0] = 1
    return f(0,2) = 2
    a = 2
    f(0,0):
       w[0] > 0: check[0] = 0
       return f(-1,0) = 0
    return f(0,0) = 0
    b = 1 + 0 = 1
    a > b: check[1] = 0
return  f(1,2) = 2
因此,这个问题的最佳解决方案是2(选择第二个元素),但您的解决方案没有选择任何元素(检查=[0,0])

这是因为
检查的更改是全局性的,而不是调用环境的本地更改,具体来说,深层次的赋值不取决于您在更高层次上所做的选择

要处理此问题,您可以:

  • 使您的列表不是全局的,每个递归调用都有自己的列表 列表的实例。“家长”呼叫将不仅选择哪一个 值,但根据此选择-父级也将 选择它将使用的列表,并将“他的”选择附加到列表中,然后转发给其父级
  • 切换到a或模拟DP解决方案,然后使用您创建的表来确定要选择的元素,如我在本线程中所述:

  • 请包括实际结果与期望结果不同的特定输入。
    f
    的返回值是多少?找到的溶液的重量?返回值应正确。注意修改递归内部的检查数组。尝试每次复制数组,并以元组形式返回它。它不是最优的,但你可以看到它better@codorw是一个由wights组成的数组,p是一个由价格组成的数组……n是项目数,剩余是最大值wight@rpax是的,返回值是正确的…我不明白你的建议,你能给我一个例子吗?我现在在手机上…很好的答案。我喜欢家庭作业问题的答案,这里没有的是代码答案,教你如何思考和解决问题。谢谢你让这个网站变得更好。@Ami很抱歉要求你提供代码……但是多给一点提示对你建议的第一个解决方案没有坏处