经典dp poj2626 chess解题报告

来源:互联网 发布:美国ge膜和陶氏膜 知乎 编辑:程序博客网 时间:2024/06/05 22:48

 题目:

Description

The Association of Chess Monsters (ACM) is planning their annual team match up against the rest of the world. The match will be on 30 boards, with 15 players playing white and 15 players playing black. ACM has many players to choose from, and they try to pick the best team they can. The ability of each player for playing white is measured on a scale from 1 to 100 and the same for playing black. During the match a player can play white or black but not both. The value of a team is the total of players' abilities to play white for players designated to play white and players' abilities to play black for players designated to play black. ACM wants to pick up a team with the highest total value. 

Input

Input consists of a sequence of lines giving players' abilities. Each line gives the abilities of a single player by two integer numbers separated by a single space. The first number is the player's ability to play white and the second is the player's ability to play black. There will be no less than 30 and no

more than 1000 lines on input.


Output

Output a single line containing an integer number giving the value of the best chess team that ACM can assemble.


Sample Input

87 84

66 78

86 94

93 87

72 100

78 63

60 91

77 64

77 91

87 73

69 62

80 68

81 83

74 63

86 68

53 80

59 73

68 70

57 94

93 62

74 80

70 72

88 85

75 99

71 66

77 64

81 92

74 57

71 63

82 97

76 56

Sample Output

2506

 


题意:

从一群人中挑选30名队员,其中15人持黑15人持白,每个人只能持一种,而且每个人持不同棋的能力值是不一样的。现在给你这一群人的持黑和持白的能力值,让你找出一种选拔方案,使得总能力值最大。

 

分析:

这是一道非常经典的dp问题,所以,我们按照dp的思考方式来想这道题。

首先要找到状态,这是核心问题。通过题目我们不难发现,如果把问题缩小一点的话,其实可以变为三个部分,从多少人中选,选

多少人持白,选多少人持黑。而这三者之间是可以相对而言独立的,因此,dp的状态也就可以分为三个维度,具体可表示为:

                                dp(i,j,k)——前i个人中选择j个人持白,k个人持黑的方案中最大的能力值是多少。

第二步就是根据状态写递推方程了,找到正确的状态后写出方程并不算难,当前状态下的最佳方案是从三个方案中择优的,即不选

当前这个人,选这个人持白,选这个人持黑。马上就可以得到dp(i,j,k)=max(dp(i-1,j,k),dp(i-1,j-1,k)+a[i],dp(i-1,j,k-1)+b[i]).

第三步划分边界最容易被忽视,这次就是没有考虑好边界的问题草草处理导致一直wrong下去。(好吧可能也是由于我太笨)。本处

的边界主要问题在于当j和k等于0时的处理,具体的方案不再赘述,读者可自行思考或看下面的代码。


反思:

这道题找状态我的确费了挺大劲,刚学dp没多久的确是自己能力还是不够,需要多练类似的问题。另外在边界问题的细节处理上还

是有些大意了。同时,写完本题后我在想,其实这题完全没必要写成三维的,可以仿照背包问题对它进行空间优化,降维至二维。


#include <iostream>#include <cmath>#include <cstring>#include <stdio.h>using namespace std;int a[1005];//记录每个人的白方得分int b[1005];//记录每个人的黑方得分int dp[1005][17][17];int main(){int i =1;memset(dp,0,sizeof(dp));//freopen("in.txt","r",stdin);while(scanf("%d%d",&a[i],&b[i])!=EOF){for(int j=0;j <=i&&j<=15;j++){for(int k =0;k<=i&&k<=15;k++){//此处j和k等于0的边界要注意if(j==0&&k==0)continue;else if(j==0){dp[i][j][k]=max(dp[i-1][j][k],dp[i-1][j][k-1]+b[i]);continue;}else if(k==0){dp[i][j][k]=max(dp[i][j][k],dp[i-1][j-1][k]+a[i]);continue;}if(j+k<=i)dp[i][j][k]=max(dp[i-1][j][k],max(dp[i-1][j-1][k]+a[i],dp[i-1][j][k-1]+b[i]));//cout << dp[i][j][k]<< " ";}}i++;}cout << dp[i-1][15][15] << endl;}

 


0 0
原创粉丝点击