【2012百度之星/初赛下】C:度度熊的礼物
描述:度度熊擁有一個(gè)自己的Baidu空間,度度熊時(shí)不時(shí)會(huì)給空間朋友贈(zèng)送禮物,以增加度度熊與朋友之間的友誼值。度度熊在偶然的機(jī)會(huì)下得到了兩種超級(jí)禮物,于是決定給每位朋友贈(zèng)送一件超級(jí)禮物。不同類(lèi)型的朋友在收到不同的禮物所能達(dá)到的開(kāi)心值是不一樣的。開(kāi)心值衡量標(biāo)準(zhǔn)是這樣的:每種超級(jí)禮物都擁有兩個(gè)屬性(A, B),每個(gè)朋友也有兩種屬性(X, Y),如果該朋友收到這個(gè)超級(jí)禮物,則這個(gè)朋友得到的開(kāi)心值為A*X + B*Y。
由于擁有超級(jí)禮物的個(gè)數(shù)限制,度度熊很好奇如何分配這些超級(jí)禮物,才能使好友的開(kāi)心值總和最大呢?
輸入
第一行n表示度度熊的好友個(gè)數(shù)。
接下來(lái)n行每行兩個(gè)整數(shù)表示度度熊好朋友的兩種屬性值Xi, Yi。
接下來(lái)2行,每行三個(gè)整數(shù)ki, Ai, Bi,表示度度熊擁有第i種超級(jí)禮物的個(gè)數(shù)以及兩個(gè)屬性值。
1<=n<=1000, 0<=Xi,Yi, Ai, Bi 1+k2>=n
輸出
輸出一行一個(gè)值表示好友開(kāi)心值總和的最大值
樣例輸入
4
3 6
7 4
1 5
2 4
3 3 4
3 4 3
樣例輸出
118
提示
送給第一種禮物的人有1,3,4,送給第二種禮物的人有2
代碼1:#include<iostream> #include<algorithm> using namespace std; int f[1001]; struct node {int x , y; }human[1001]; int num1,num2,a1,b1,a2,b2;int main(void) {int n , i , j , ans;scanf("%d",&n);for(i = 1 ; i <= n ; ++i)scanf("%d %d" , &human[i].x , &human[i].y);scanf("%d %d %d" , &num1 , &a1 , &b1);scanf("%d %d %d" , &num2 , &a2 , &b2);memset(f,-1,sizeof(f));//printf("%d\n",f[1]);ans = -1000000;f[0] = 0;for(i = 1 ; i <= min(n,num2) ; ++i)f[i] = f[i-1] + human[i].x*a2 + human[i].y*b2;if(f[n] > ans)ans = f[n];//f[0]=human[1].a*a1+human[1].b*b1;//printf("ans:%d\n",ans);for(i = 1 ; i <= min(num1,n) ; ++i){f[0] = f[0] + human[i].x*a1 + human[i].y*b1;//printf("i:%d j:0 f:%d\n",i,f[0]);for(j = 1 ; j <= min(n-i,num2) ; ++j){f[j] = max(f[j-1]+human[i+j].x*a2+human[i+j].y*b2 , f[j]+human[i+j].x*a1+human[i+j].y*b1);//printf("i:%d j:%d f:%d\n",i,j,f[j]);}if(f[n-i] > ans)ans = f[n-i];}printf("%d\n",ans);return 0; }
代碼2:
#include<iostream> using namespace std;int c[1000][2000];int maxx(int a,int b) {if(a > b)return a;elsereturn b; }int main(void) {int i , j , t , n , k1 , k2 , a1 , a2 , b1 , b2 , max;int x[1001] , y[1001];cin >> n;for (i = 1 ; i <= n ; ++i)cin >> x[i] >> y[i];cin >> k1 >> a1 >> b1 >> k2 >> a2 >> b2;t = maxx(x[1]*a1+y[1]*b1,x[1]*a2+y[1]*b2);c[1][k1+k2] = x[1]*a1+y[1]*b1;c[1][0] = x[1]*a2+y[1]*b2;for(i = 1 ; i <= k1+k2-1 ; ++i)c[1][i] = t;for(j = 2 ; j <= n ; ++j){for(i = 0 ; i <= k1+k2-j+1 ; ++i)c[j][i] = maxx(c[j-1][i+1]+x[j]*a1+y[j]*b1,c[j-1][i]+x[j]*a2+y[j]*b2);}max = 0;for(i = 0 ; i <= k1+k2-n+1 ; ++i){if(c[n][i] > max)max = c[n][i];}cout << max << endl;return 0; } DP方法:#include<iostream> #include<cstdio> using namespace std;const int MAXN = 1002; int x[MAXN], y[MAXN], dp[MAXN][MAXN], a[3], b[3], k[3]; int main(void) {int n , i , j , ans , c1 ,c2;while(scanf("%d", &n) != EOF){for (i = 1; i <= n; ++i){scanf("%d %d", &x[i], &y[i]);}for (i = 1; i <= 2; ++i){scanf("%d %d %d", &k[i], &a[i], &b[i]);}memset(dp , 0 , sizeof(dp));for (i = 1; i <= n; ++i){for (j = 0; j <= k[1] && j <= i; ++j){if (i - j > k[2])continue;c1 = a[1] * x[i] + b[1] * y[i] ;c2 = a[2] * x[i] + b[2] * y[i] ;if(j)dp[i][j] = dp[i - 1][j - 1] + c1;if(i - j)dp[i][j] = max(dp[i][j], dp[i - 1][j] + c2);}}ans = 0;for (i = 0; i <= k[1]; ++i)ans = max(ans, dp[n][i]);printf("%d\n", ans);}return 0; }
總結(jié)
以上是生活随笔為你收集整理的【2012百度之星/初赛下】C:度度熊的礼物的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 【2012百度之星/初赛下】B:网页聚类
- 下一篇: 程序员面试100题之十五:数组分割