// bag_pro.cpp : 定义控制台应用程序的入口点。
//
// stdafx.cpp : 只包括标准包含文件的源文件
// bag.pch 将作为预编译头
// stdafx.obj 将包含预编译类型信息
// TODO: 在 STDAFX.H 中引用任何所需的附加头文件,
//而不是在此文件中引用
// bag.cpp : 定义控制台应用程序的入口点。
//
#include "stdafx.h"
#include<iostream>
#include<algorithm>
#define maxsize 200
using namespace std;
/*
有一个容量为V的背包,和一些物品。这些物品分别有两个属性,体积w和价值v,
每种物品只有一个。要求用这个背包装下价值尽可能多的物品,求该最大价值,
背包可以不被装满。因为最优解中,每个物品都有两种可能的情况,即在背包中
或者不存在(背 包中有0个该物品或者 1个),所以我们把这个问题称为0-1背
包问题。
n个物品;m代表背包容量;w代表每个物体的体积;v代表每个物体的价值
dp[i][j] = max{dp[i-1][j-v[i]] + w[i],dp[i-1][j]};
改进:
dp[i-1][j]}的特点,当前状态仅依赖前一状态的剩余体积与当前物品体积v[i]
的关系。根据这个特点,我们可以将dp降到一维
即dp[j] = max{dp[j],dp[j-w[i]]+v[i]}。从这个方程中我们可以发现,
有两个dp[j],但是要区分开。等号左边的dp[j]是当前i的状态,右边中括号内
的dp[j]是第i-1状态下的值。
测试数据
//in.txt:
5 100
77 92
22 22
29 87
50 46
99 90
//out.txt
133
//in.txt:
8 200
79 83
58 14
86 54
11 79
28 72
62 52
15 48
68 62
//out.txt
334
复杂度:o(n*m)
*/
int w[maxsize], v[maxsize], dp[maxsize];
int main()
{
int n, m; //n代表物品的个数,m代表背包总容量
cin >> n >> m;
for (int i = 1; i <= n; i++)
{
cin >> w[i] >> v[i];
}
//初始化
for (int i = 1; i <= m; i++)
{
dp[i] = 0;
}
// 找最优解
for (int i = 1; i <= n; i++) //i从1开始
{
//只有 j > w[i] , dp[i][j] 才能取最大值,否则dp[j]将不作更新,等于dp[i-1][j]
for (int j =m; j > w[i]; j--)
{
dp[j] = max(dp[j], dp[j - w[i]] + v[i]);
}
}
cout << dp[m] << endl;
system("pause");
return 0;
}