[简单DP] COJ 1123 PK武林盟主

状态转移方程p[i,j] = 0.5*(p[i-1,j]+p[i,j-1])。

浮点数运算,初始时要向上取整。

# include <stdio.h>

# include <math.h>

# include <string.h>



int ap1, ap2, hp1, hp2;



double f[1005][1005];



double cal(int x, int y)

{

    if (f[x][y] >= 0) return f[x][y];

    if (x <= 0) return f[x][y] = 0;

    if (y <= 0) return f[x][y] = 100;

    return f[x][y] = 0.5*(cal(x, y-1)+cal(x-1, y));

}



int main()

{

    int n, i, j, m;

    while (~scanf("%d%d%d%d", &hp1, &hp2, &ap1, &ap2))

    {

        n = (int)ceil(1.0*hp1/ap2), m = (int)ceil(1.0*hp2/ap1);

        for (i = 0; i <= n; ++i)

        for (j = 0; j <= m; ++j)

            f[i][j] = -1;

        printf("%.4f\n", cal(n, m));

    }

    

    return 0;

}

在HDOJ上是RE的(ACCESS_VOALATION),原因是确实下标引用出界了(这里没有限制比率范围,只能用组合的方法来做):

假设经过x次胜出,则x<n+m,且x>=n,于是有p = 0.5^n*C(n,n)+0.5^(n+1)*C(n+1,n)+...+0.5^(n+m-1)*C(n+m-1,n),后项项可以通过前项迭代得到,浮点运算,可以先取对数。

你可能感兴趣的:(dp)