问题:
有 n 个物品,每个物品都有各自的体积和价值。给定一个容量给定的背包,如何使背包中物品的总价值最大?
问题分析:
在选择放入背包的物品时,物品i只有两个选项,放入背包或者不放入背包。物品i不能多次放入背包,也不能只将物品i的一部分放入背包。设xi表示物品i放入背包的情况,当xi=0时,表示不放入背包;当xi=1时,表示放入背包。
在做出决策xi的时候,问题处于以下两种状态之一:
1.如果背包容量不足以容纳物品i,则xi = 0,背包中物品的价值不会增加。
2. 如果背包容量足以容纳物品i,则xi = 1,背包中物品的价值增加vi
在两种情况下,价值最大的背包的价值应该是对 xi 进行决策后的价值
设计:
通过两个数组和值来记录物品的重量和价值。
通过两个for循环,将一个物品添加到背包中,直到可以将最后一个物品添加到背包中(如果背包承重允许)。
只需在 for 循环中添加一个检查,检查产品重量是否小于背包载重,如果小于,则重量为 j 的背包的最大值为 max(c[i-1][j],c[i-1][j-[i]]+value[i])。
for(int i = 1; i <= num; i++){
for(int j = 1; j <= totalweight; j++){
if(j < weight[i]){
c[i][j] = c[i-1][j];
// cout << "[" << i << "],[" << j << "]:" << c[i][j] << " ";
}else{
c[i][j] = max(c[i-1][j],c[i-1][j-weight[i]]+value[i]);
// cout << "[" << i << "],[" << j << "]:" << c[i][j];
}
}
cout << endl;
}
到此背包算法其实已经实现了,最后我们只需要输出c[num][]就可以得到背包的最大值了。
以下是源代码:
//背包算法
#include
#include
using namespace std;
const int MAX = 1000;
int main(){
int totalweight;
int num;
cout << "==========背包问题========" << endl;
cout << "======输入背包最大载重======" << endl;
cin >> totalweight;
cout << "========输入物品个数=======" << endl;
cin >> num;
int weight[MAX] = {0};
int value[MAX] = {0};
cout << "=====输入商品重量和价值=====" << endl;
for(int i = 1; i <= num;i++)
cin >> weight[i] >> value[i];
int c[MAX][MAX];
for(int j = 0; j <= totalweight; j++){
c[0][j] = 0;
}
for(int i = 0; i <= num; i++){
c[i][0] = 0;
}
for(int i = 1; i <= num; i++){
for(int j = 1; j <= totalweight; j++){
if(j < weight[i]){
c[i][j] = c[i-1][j];
// cout << "[" << i << "],[" << j << "]:" << c[i][j] << " ";
}else{
c[i][j] = max(c[i-1][j],c[i-1][j-weight[i]]+value[i]);
// cout << "[" << i << "],[" << j << "]:" << c[i][j];
}
}
cout << endl;
}
cout << "=====背包最大价值为=====" << endl;
cout << c[num][totalweight] << endl;
}