SERKOI最新推出了一种叫做“免费馅饼”的游戏。
游戏在一个舞台上进行。舞台的宽度为W格,天幕的高度为H格,游戏者占一格。开始时游戏者站在舞台的正中央,手里拿着一个托盘。下图为天幕的高度为4格时某一个时刻游戏者接馅饼的情景。
游戏开始后,从舞台天幕顶端的格子中不断出现馅饼并垂直下落,下落速度1格/秒。游戏者左右移动去接馅饼。游戏者每秒可以向左或向右移动一格或两格,也可以站在原地不动。
馅饼有很多种,游戏者事先根据自己的口味,对各种馅饼依次打了分。当馅饼在某一秒末恰好到达游戏者所在的格子中,游戏者就收集到了这块馅饼。
写一个程序,帮助我们的游戏者收集馅饼,使得所收集馅饼的分数之和最大。
免费馅饼可以用动态规划算法解决。
状态方程如下:
F[i][j]=max(F[i-1],F[j-k])+A[i][j];(-2<=k<=2)
表示第 i 秒在第 j 个格中收集到的最大饼值。
A[i][j] 表示第i秒中方格j可以收集到的饼值。
动态规划解免费馅饼代码如下:
#include<cstring>
#include<stdlib.h>
int w=0,h=0,t=0;
int all=0,at=0,ak=0;
int a[1010][110];
int f[1010][110];
int g[1010][110];
FILE *fp,*fp2;
void output(int at,int ak)
{
    if(at<=0) 
        return;
    output(at-1,ak-g[at][ak]);
    fprintf(fp2,“%d\n“,g[at][ak]);
}
int main()
{
    fp=fopen(“in.txt”,“r”);
    fp2=fopen(“out.txt”,“w”);
    fscanf(fp,“%d%d”,&w,&h); //读取w和h
    for(int i=0;i<=100;++i)//初始化 
        for(int j=1;j<=100;++j)
        {
            f[i][j]=-1000;
            a[i][j]=0;
            g[i][j]=0;
        }
    int t1,w1,s1;//时间,位置,分数 
    while(fscanf(fp,“%d%d%d”,&t1,&w1,&s1)!=EOF){
        a[t1+(h-1)][w1]+=s1;         
    }
    fclose(fp);
    t=t1+(h-1); //总时间 
    f[0][(w+1)/2]=a[0][(w+1)/2];//0时刻 
    for(int i=1;i<=t;++i){
        for(int j=1;j<=w;++j){
            for(int k=2;k>=-2;k-)
            {
                if(j-k>0&&j-k<=w&&f[i-1][j-k]>f[i][j]){
                    f[i][j]=f[i-1][j-k];
                    g[i][j]=k;
                }
            }
            f[i][j]+=a[i][j];
            if(f[i][j]>all){
                all=f[i][j];
                at=i;
                ak=j;
            }
        }
    }
    fprintf(fp2,“%d\n“,all);
    output(at,ak);
    fclose(fp2);
    return 0;
}
样例输入
3 3
0 1 5 
0 2 3
1 2 3
1 3 4
样例输出
9
-1 
0
2
哈哈 这种类似的游戏我以前用VB编过。。。不过大学之后 就再没接触计算机语言方面的东西了。。
ps 我给你发邮件了 期待答复~