求解整数背包(Solving the Integer Knapsack)

2019-07-29 22:45发布

我一个新的动态编程,并在这里SPOJ试图整数背包问题(http://www.spoj.pl/problems/KNAPSACK/ )。 然而,对于给定的测试用例我的解决方案是不是给正确的输出。 我很感谢你,如果你能提出如果我下面的实现是正确的。 请注意,变量back是回溯,对此我不知道该怎么办。 我希望能有你太贯彻回溯帮助。 谢谢。

#include <cstdio>
#include <cstdlib>
#include <algorithm>
#include <vector>
#include <string>
#include <iostream>

using namespace std;

int knapsack(int value[], int weight[], int n, int C,
         vector < int >&back)
{
    int *M = new int[C + 1];
    int k;
    int i, j, tmp, pos;
    for (i = 1; i <= C; i++) {
        M[i] = M[i - 1];
        pos = i - 1;
        for (j = 0; j < n; j++) {
            k = i - weight[j];
            if (k >= 0)
                tmp = M[k] + value[j];
            if (tmp > M[i]) {
                M[i] = tmp;
            }
        }
        back.push_back(pos);
    }
    int ans = M[C];
    delete[]M;
    return ans;
}


int main()
{
    int C, N;
    cin >> C >> N;
    int* value = new int[N+1];
    int* weight = new int[N+1];
    for ( int i = 0; i <= N; i++) {
        cin>>value[i]>>weight[i];
    }
    vector < int >back(N, 0);
    cout<<knapsack(value,weight,N,C,back)<<endl;
    return 0;
}

下面是正确的输入/输出的测试案例:

Input:
4 5
1 8
2 4
3 0
2 5
2 3


Output:
13

但是,我得到的输出为17

Answer 1:

这是被称为0-1背包的背包问题的一个版本。

你在你的代码做一些愚蠢的错误。

与在输入所述第一整数开始是权重和第二是值。 当你正在采取先为值和第二的重量。 此外正在服用n + 1个值作为输入0到N以下。

现在,在你的算法,你正在考虑,你可以采取任何数量的项目的副本,这是不正确的,这是一个0-1背包。 阅读本http://en.wikipedia.org/wiki/Knapsack_problem 。

我想出了这个算法,我提出和被录取了。 因此,这应该能正常运行。

int M[2000][2000];
int knapsack(int value[], int weight[], int C, int n)
{      
  for(int i = 1; i <= C; i++){
    for(int j = 0; j <n; j++){
      if(j > 0){
        M[j][i] = M[j-1][i];
        if (weight[j] <= i)
          M[j][i] = max(M[j][i], M[j-1][i-weight[j]]+value[j]);
      }
      else{
        M[j][i] = 0;
        if(weight[j] <= i)
          M[j][i] = max(M[j][i], value[j]);
      }
    }
    //    cout << M[i][n-1] << endl;
  }        
  return M[n-1][C];
}  

int main()
{
    int C, N;
    cin >> C >> N;
    //    cout << C << endl;
    int* value = new int[N+1];
    int* weight = new int[N+1];
    for ( int i = 0; i < N; i++) {
        cin>>weight[i]>>value[i];
    }
    //   vector < int >back(N, 0);
    cout<<knapsack(value,weight,C,N)<<endl;
    return 0;
}

顺便说一句不动态地分配阵列简单地使用矢量

vector <int> My_array(n);


Answer 2:

有一个在记录以及背包问题的一个版本https://sites.google.com/site/mikescoderama/Home/0-1-knapsack-problem-in-p Python编写的。

编辑:没关系,我跳过其中的第一行输入定义C和N的一部分说,你输入例子似乎并不与你提供的代码加载(它正在寻找一个更比对,由于在将预期<= N)。 我想到的是循环应该是<N,得到0到n-1项目。

修复,我得到印134516145的结果,这是荒谬的。



文章来源: Solving the Integer Knapsack