Codefroces 366 C Dima and Salad(dp)
题意:一共有n种水果,每种水果都有一个ai, bi,现求一个最大的ai总和,使得ai之和/对应的bi之和的值等于K。
题解:将bi转换成偏移量,只要偏移到起点位置,就代表左右偏移抵消了,就满足题意了,注意一点的是这个跑法和01背包的恰好消耗是一样的初始化方法,将起点设为0,其他位置设为-INF,这样状态只能从起点转移出去,然后再从外面存在的点转移出去。
代码:
1 #include<iostream> 2 #include<cstring> 3 using namespace std; 4 const int INF = 0x3f3f3f3f; 5 const int N = 1e5+5; 6 int a[N], b[N], ans[N]; 7 int main() 8 { 9 ios::sync_with_stdio(false); 10 cin.tie(0); 11 cout.tie(0); 12 int n, k; 13 cin >> n >> k; 14 for(int i = 1; i <= n; i++) 15 cin >> a[i]; 16 for(int i = 1; i <= n; i++) 17 { 18 cin >> b[i]; 19 b[i] = a[i] - b[i]*k; 20 } 21 memset(ans, -INF, sizeof(ans)); 22 ans[25000] = 0; 23 for(int i = 1; i <= n; i++) 24 { 25 if(b[i] >= 0) 26 { 27 for(int j = 50000; j >= b[i]; j--) 28 ans[j] = max(ans[j-b[i]]+a[i], ans[j]); 29 } 30 else 31 for(int j = 0; j <= 50000-b[i]; j++) 32 ans[j] = max(ans[j], ans[j-b[i]]+a[i]); 33 } 34 if(ans[25000] == 0) cout << -1 << endl; 35 else cout << ans[25000] << endl; 36 return 0; 37 }