C++ 中的背包回溯算法是否有解决方案而不是 move

Is there a solution instead of move for knapsack backtracking algorithm in C++

我使用了Backtracking of Knapsack solution with C++的解决方案。我从这里再次得到了解决方案。 Knapsack solution with Backtraking in c++ 我的编译器在行移动时出错。有没有不使用 move 的解决方案?如何在不使用 move 的情况下修改代码?

#include<iostream>
#include<vector>

using namespace std;

int weights[] = {2, 3, 1}, values[] = {6, 15, 7};

int solution = 0, n = 3;

std::vector<int> vsol;
std::vector<int> temp;

bool issol;


void Knapsack (int i, int max, int value)
{
  for (int k = i; k < n; k++) {
    if ( max > 0)
    {
        if (weights[k] <= max)
        {
          temp.push_back(k);
          if (value+ values[k] >= solution)
          {
            solution = value + values[k];
            issol = true;
          }
        }
        if ( (k+1) < n)
        {
          Knapsack (k+1, max - weights[k], value + values[k]);
        }
        else
        {
          if (issol == true)
          {
            if (! vsol.empty()) vsol.clear();
            std::move(temp.begin(), temp.end(), std::back_inserter(vsol));
            temp.clear();
            issol = false;
          } else temp.clear();
          return;
        }
    }
    else
    {
        if (issol == true)
        {
            if (! vsol.empty()) vsol.clear();
            std::move(temp.begin(), temp.end(), std::back_inserter(vsol));
            temp.clear();
            issol = false;
        } else temp.clear();
        return;
    }
  }
}

int main()
{
    Knapsack(0, 2, 0);
    cout << "solution: " << solution << endl;
    for(vector<int>::iterator it = vsol.begin(); it != vsol.end(); it++)
        cout << *it << " ";
    return 0;
}

您可以更改 std::move with std::copy。通常它们是不等价的,但在这里您使用的是 int 向量(因此没有性能损失)并且源数组会立即被清除 (temp.clear()).

所以你可以这样写:

if (!vsol.empty()) vsol.clear();
std::copy(temp.begin(), temp.end(), std::back_inserter(vsol));

确实想多了。简单的:

vsol = temp;

清晰、快速并且也适用于 C++98(取决于您的 C++Builder 版本,C++11 兼容性可能是个问题)。

修改版本:

#include <iostream>
#include <vector>

int weights[] = {2, 3, 1}, values[] = {6, 15, 7};

int solution = 0, n = 3;

std::vector<int> vsol;
std::vector<int> temp;

bool issol;

void Knapsack(int i, int max, int value)
{
  for (int k = i; k < n; ++k)
  {
    if (max > 0)
    {
      if (weights[k] <= max)
      {
        temp.push_back(k);
        if (value + values[k] >= solution)
        {
          solution = value + values[k];
          issol = true;
        }
      }

      if (k + 1 < n)
      {
        Knapsack(k + 1, max - weights[k], value + values[k]);
      }
      else
      {
        if (issol)
        {
          vsol = temp;
          issol = false;
        }

        temp.clear();
        return;
      }
    }
    else
    {
      if (issol)
      {
        vsol = temp;
        issol = false;
      }

      temp.clear();
      return;
    }
  }
}

int main()
{
  Knapsack(0, 2, 0);
  std::cout << "solution: " << solution << '\n';
  for(std::vector<int>::iterator it = vsol.begin(); it != vsol.end(); ++it)
    std::cout << *it << " ";

  return 0;
}