1. 程式人生 > 實用技巧 >01揹包

01揹包

測試地址:here

AC_Code:

 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 typedef long long ll;
 4 typedef unsigned long long ull;
 5 const int maxn = 1010;
 6 const int mod = 2333333;
 7 const int inf = 0x3f3f3f3f;
 8 #define gok ios::sync_with_stdio(false);cin.tie(0);cout.tie(0)
 9 #define pii pair<int,int>
10
#define fi first 11 #define se second 12 #define pb push_back 13 #define rep(i,first,second) for(ll i=first;i<=second;i++) 14 #define dep(i,first,second) for(ll i=first;i>=second;i--) 15 #define erep(i,u) for(ll i=head[u];~i;i=e[i].nxt) 16 //0-1揹包 17 /* 18 f[i][j]只看前i個物品,總體積是j的情況下,總價值最大是多少 19 ans = max(f[n][0~v]);
20 21 1.f[i][j] = f[i-1][j]; //不選 22 2.f[i][j] = f[i-1][j-v[i]]; //選 23 f[i][j] = max(1,2); 24 25 初始化f[0][0]=0; 26 O(N*V) 27 */ 28 int n,m; 29 int dp[maxn][maxn]; 30 int v[maxn],w[maxn]; 31 32 int main() 33 { 34 gok; 35 cin>>n>>m; 36 rep(i,1,n) cin>>v[i]>>w[i];
37 rep(i,1,n){ 38 rep(j,0,m){ 39 dp[i][j]=dp[i-1][j]; 40 if( j>=v[i] ){ 41 dp[i][j]=max(dp[i][j],dp[i-1][j-v[i]]+w[i]); 42 } 43 } 44 } 45 int res=0; 46 rep(i,1,m) res=max(res,dp[n][i]); 47 cout<<res<<'\n'; 48 return 0; 49 }

優化版AC_Code:

 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 typedef long long ll;
 4 typedef unsigned long long ull;
 5 const int maxn = 1010;
 6 const int mod = 2333333;
 7 const int inf = 0x3f3f3f3f;
 8 #define gok ios::sync_with_stdio(false);cin.tie(0);cout.tie(0)
 9 #define pii pair<int,int>
10 #define fi first
11 #define se second
12 #define pb push_back
13 #define rep(i,first,second) for(ll i=first;i<=second;i++)
14 #define dep(i,first,second) for(ll i=first;i>=second;i--)
15 #define erep(i,u) for(ll i=head[u];~i;i=e[i].nxt)
16 //0-1揹包
17 /*
18 f[i][j]只看前i個物品,總體積是j的情況下,總價值最大是多少
19 ans = max(f[n][0~v]);
20 
21 1.f[i][j] = f[i-1][j];        //不選
22 2.f[i][j] = f[i-1][j-v[i]];   //選
23 f[i][j] = max(1,2);
24 
25 初始化f[0][0]=0;
26 O(N*V)
27 */
28 
29 /*
30 f[i]的狀態只與f[i-1]有關,所以用滾動陣列
31 
32 */
33 int n,m;
34 int dp[maxn];
35 int v[maxn],w[maxn];
36 
37 int main()
38 {
39     gok;
40     cin>>n>>m;
41     rep(i,1,n) cin>>v[i]>>w[i];
42     rep(i,1,n){
43         dep(j,m,v[i]){//要保證dp[j-v[i]],用的是i-1的,所以倒著,否則j-v[i]在j之前已經算過,那麼更新的時候用的就是dp[i][j-v[i]],而不是原來dp[i-1][j-v[i]];
44             dp[j]=max(dp[j],dp[j-v[i]]+w[i]);
45         }
46     }
47     cout<<dp[m]<<'\n';
48 
49     return 0;
50 }