• hdu 6377 : 度度熊看球赛


    题目链接

    题解:

    • 将原问题转换为 对于全部 (2n)! 种情况,每种情况对ans的贡献为 D^k,其中k表示该情况下有k对情侣座位相邻。
    • 预处理好共有 i (1<=i<=N)对情侣时,出现 j (0<=j<=i) 对情侣坐在一起时情况数,用dp[i][j]记录
    • 初始条件为dp[1][1]=2
    • 当总情侣对数由 i 向 i+1 转移时,j 有四种变化的可能
    1. j-1 → j : 新来的情侣“一起”插入到不打断先前情侣的“相邻”座位处 dp[i+1][j] += 2 * dp[i][j-1] * (2*i+1-(j-1))
    2. j → j : 新来的情侣“一起”插入到打断先前某对情侣的“相邻”座位处 dp[i+1][j] += 2 * dp[i][j] * j ,或者“分开”插入到不打断先前情侣的“不相邻”座位处  dp[i+1][j] += 2 * dp[i][j] * C(2*i+1-j,2)
    3. j+1 → j : 新来的情侣,一个插入到打断先前某对情侣的座位处,另一个插入到不打断先前情侣的座位处 dp[i+1][j] += 2 * dp[i][j+1] * (j+1)*(2*i+1-(j+1)
    4. j+2 → j : 新来的情侣“分开”插入到打断先前某两对情侣的“相邻”座位处 dp[i+1][j] += 2 * dp[i][j+2] * C(j+2,2)
    • 以上为预处理过程
    • 最后 ans += d^i * dp[n][i] ,i=0→n

    代码如下

    #include<bits/stdc++.h>
    using namespace std;
    typedef long long LL;
    
    const LL mod=998244353;
    
    LL qpow(LL x,LL n)        //求x^n%mod
    {
        LL ret=1;
        for(; n; n>>=1)
        {
            if(n&1) ret=ret*x%mod;
            x=x*x%mod;
        }
        return ret;
    }
    
    int C(LL a,LL b=2)
    {
        return a*(a-1)%mod*qpow(b,mod-2)%mod;
    }
    
    const int N=1e3+5;
    LL dp[N][N];
    
    void init()
    {
        dp[1][1]=2;
        for(int i=1;i<N;i++)
        {
            dp[i+1][0]=2*dp[i][0]%mod*C(2*i+1,2)%mod+
                       2*dp[i][1]%mod*2*i%mod+
                       2*dp[i][2]%mod;
            dp[i+1][0]%=mod;
            for(int j=1;j<=i+1;j++)
            {
                dp[i+1][j]=2*dp[i][j-1]%mod*(2*i+1-(j-1))%mod+
                           2*dp[i][j]%mod*(j+C(2*i+1-j,2))%mod+
                           2*dp[i][j+1]%mod*((j+1)*(2*i+1-(j+1))%mod)%mod+
                           2*dp[i][j+2]%mod*C(j+2,2)%mod;
                dp[i+1][j]%=mod;
            }
        }
    }
    
    int main()
    {
        init();
        LL n,d;
        while(~scanf("%lld%lld",&n,&d))
        {
            LL ret=0;
            if(n==1)
            {
                printf("%lld
    ",2*d%mod);
                continue;
            }
            for(int i=0;i<=n;i++) ret=(ret+dp[n][i]*qpow(d,i)%mod)%mod;
            printf("%lld
    ",ret);
        }
    }
  • 相关阅读:
    发送邮件程序
    T-SQL存储过程、游标
    GPS经纬度换算成XY坐标
    开博了
    你应该知道的 50 个 Python 单行代码
    想提升java知识的同学请进
    adb工具包使用方法
    红米note3刷安卓原生
    hadoop 使用和javaAPI
    django学习——url的name
  • 原文地址:https://www.cnblogs.com/Just--Do--It/p/9460904.html
Copyright © 2020-2023  润新知