-
輸入:
-
每組測試資料可能有多組輸入,對於每一組輸入,
輸入的第一行包括兩個整數S(1 <= S <= 1000)和C(1<=C<=100),S代表地鐵的總空間的大小,C代表v一共儲存的炸藥的個數。
接下來的C行每行包括兩個1到100(包括1和100)的整數,分別表示這個炸藥所需要的空間以及它所能產生的破壞力。
-
輸出:
-
對於每組輸入,輸出只包括一行,這一行只包含一個整數,表示在地鐵的有限的空間裡轉載選出的炸藥,能產生的最大的破壞力。如果每個炸藥的體積都很大,地鐵的空間連一個炸藥都裝不下,輸出0即可。
-
範例輸入:
-
70 371 10069 11 2
-
範例輸出:
-
3
#include <stdio.h>
int max(int i,int j){
return i>j ? i:j;
}
int main(){
int c,n;
while(scanf("%d %d",&c,&n) != EOF){
int carr[101] = { 0 }; //炸彈的空間
int parr[101] = { 0 }; //炸彈的威力
int s[1000] = { 0 }; //儲存當前容量,的最大威力
for(int i=1; i<=n; i++)
scanf("%d %d",&carr[i],&parr[i]);
for(int i=1; i<=n; i++){
for(int j=c; j>0; j--){
int t = 0;
if(j >= carr[i])
t = s[j-carr[i]] + parr[i];
s[j] = max(s[j],t);
}
}
printf("%d\n",s[c]);
}
return 0;
}
/**************************************************************
Problem: 1364
User: 從此醉
Language: C
Result: Accepted
Time:200 ms
Memory:908 kb
****************************************************************/
第二種實現:
下面貼出:空間複雜度n*v的Java代碼,以便理解上面的代碼:
public class 背包01 { public static int capsity = 10; static int n = 3; public static int weights[] = {0,3,4,5,}; private static int values[] = {0,4,5,6}; static int opts[][] = new int[n+1][capsity+1]; public static void main(String[] args) { for(int i=1; i<=n; i++){ for(int j=1; j<=capsity; j++){ if(weights[i] <= j){ //關鍵的一步 opts[i][j] = Math.max(opts[i-1][j], opts[i-1][j-weights[i]]+values[i]); }else opts[i][j] = opts[i-1][j]; } } for(int i=0; i<=n; i++){ for(int j=0; j<=capsity; j++){ System.out.printf("%3d",opts[i][j]); } System.out.println(); } System.out.println("最後的結果:"+opts[n][capsity]); }}
output:
0 0 0 0 0 0 0 0 0 0 0
0 0 0 4 4 4 4 4 4 4 4
0 0 0 4 5 5 5 9 9 9 9
0 0 0 4 5 6 6 9 10 11 11
最後的結果:11
3、遞迴實現: