http://acm.hdu.edu.cn/showproblem.php?pid=5045
m个人n题,每个人做对的概率给定,一道题只能一个人做。他做的时候其他人休息,问你如何分配能使作对概率最大。
有一个限制条件,每时每刻做题的时候,每个人做题数差值不能大于2。
解决方法很巧妙,先让没做过题的人做,如果都做过,那么就清零。在来。。
递推的过程没什么说的,
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
using namespace std;
const int maxn=200;
double a[13][1002];
double dp[1002][1050];
int main()
{ int t;
int m,n;
scanf("%d",&t);
for(int tt=1;tt<=t;tt++){
scanf("%d%d",&n,&m);
for(int i=1;i<=n;i++)
for(int j=1;j<=m;j++)
cin>>a[i][j];
for (int i=0;i<=m;i++)
for (int j=0;j<=(1<<n)-1;j++)
dp[i][j]=-1;
dp[0][0]=0;
int peo=0;
for (int j=1;j<=m;j++)
for (int i=0;i<(1<<n);i++)
if (dp[j-1][i]!=-1)
for (int k=1;k<=n;k++)
{
peo=1<<(k-1);
if ((i&peo)==peo) continue;
peo|=i;
if (peo==(1<<n)-1) peo=0;
dp[j][peo]=max(dp[j][peo],dp[j-1][i]+a[k][j]);
}
double ans=0;
for(int i=0;i<(1<<n);i++){
ans=max(ans,dp[m][i]);
}
printf("Case #%d: %.5f\n",tt,ans);
}
return 0;
}