其他分享
首页 > 其他分享> > 「CTS2019 | CTSC2019」随机立方体 解题报告

「CTS2019 | CTSC2019」随机立方体 解题报告

作者:互联网

「CTS2019 | CTSC2019」随机立方体

据说这是签到题,但是我计数学的实在有点差,这里认真说一说。


我们先考虑一些事实

以上两个事实都可以启发我们往容斥的方向想,考虑容斥。

设\(dp_i\)为至少有\(i\)个极大数字的方案数,然后我们进行钦定。

\(dp_i\)等于(钦定\(i\)个极大数的位置方案数)\(\times\)(极大数删去平面的交的填充方案数)\(\times\)(剩下随意发挥的剩余正方体填充方案数)

首先我们需要把所有的数字分成两部分,删去的平面交与剩余的正方体。

这里设\(N=n\times m\times l\),\(g_i\)为钦定\(i\)个极大值后删去平面交的方块数,那么这个数字的划分方案数就是\(\binom{N}{g_i}\)

\(g_i\)的表达式也很简单,\(g_i=nml-(n-i)(m-i)(l-i)\)

然后挨个考虑\(dp\)的组成成分,设\(f_i\)等于钦定\(i\)个极大的位置的方案数,因为每次都是子问题,所以实际上很简单
\[ f_i=\prod_{j=0}^{i-1}(n-j)(m-j)(l-j) \]
设\(h_i\)表示删去的平面交的填充方案数,可以发现,这个东西一下子求不来,可以考虑一下递推的方法。

我们再考虑一个事实

这启发我们先进行数值大的外面的填充

我们先把\(g_i\)个数中最大的数值拿出来,填到对应位置,然后剩下的\(g_i-g_{i-1}+1\)个位置(就是第\(i\)次删去的平面),每个位置可以随便选择一个数,方案数为\(\frac{(g_i-1)!}{g_{i-1}!}\),然后我们可以发现,剩下的数的填充就是子问题\(h_{i-1}\)

于是我们可以得到
\[ \begin{aligned} h_i&=\frac{(g_i-1)!}{g_{i-1}!}\times h_{i-1}\\ &=\prod_{j=0}^{i-1}\frac{(g_{j+1}-1)!}{g_j!} \end{aligned} \]
最后面随意填充就简单了就是\((N-g_i)!\)

然后我们带回去化简一下
\[ \begin{aligned} dp_i&=\binom{N}{g_i}f_ih_i(N-g_i)!\\ &=N!f_i\prod_{j=1}^{i}(g_j-1)!\prod_{j=0}^{i}\frac{1}{g_j!}\\ &=N!f_i\prod_{j=1}^{i}\frac{1}{g_j} \end{aligned} \]
我们现在求的是方案数,但题意是概率。所以这个\(N!\)其实直接扔了就好。

令\(dp_i\)代表至少\(i\)个极大数的概率,那么
\[ dp_i=f_i\prod_{j=1}^i\frac{1}{g_j} \]
我们知道,如果\(a\times b=c\),那么可以有
\[ a^{-1}\equiv c^{-1}b\pmod p \]
有了这个,我们就可以线性求\(g\)的逆元了,这也是我们熟知的阶乘逆元的方法。

还有最后一步,设\(ans_i\)为恰好\(i\)个极大数的概率

设\(mi=\min(n,m,l)\)

我们有
\[ dp_i=\sum_{j=i}^{mi}ans_j\binom{j}{i} \]
由二项式反演可得
\[ ans_i=\sum_{j=i}^{mi}dp_j\binom{j}{i}(-1)^{j-i} \]


什么?你不会二项式反演?(其实我自己忘了就尝试推了一会儿,但我并不会比较感性理解的,只会一个推式子的


\[ A_i=\sum_{j=i}^n\binom{j}{i}B_j \]
设\(\delta_{i,j}\)为满足
\[ B_i=\sum_{j=i}^n\delta_{i,j}A_j \]
的东西,考虑求出Ta
\[ \begin{aligned} B_i&=\sum_{j=i}^n\delta_{i,j}A_j\\ &=\sum_{j=i}^n\delta_{i,j}\sum_{k=j}^n\binom{k}{j}B_k\\ &=\sum_{k=i}^nB_k\sum_{j=i}^k\delta_{i,j}\binom{k}{j} \end{aligned} \]
可以得到,我们需要满足
\[ \sum_{j=i}^k\delta_{i,j}\binom{k}{j}=[k=i] \]
在优秀的莫比乌斯反演的某步证明中,我们用到了这个式子
\[ \sum_{i=0}^n(-1)^i\binom{n}{i}=[n=0] \]
证明方法很多,不说了

随便把这个式子变一变
\[ \sum_{j=i}^k(-1)^{j-i}\binom{k-i}{k-j}=[k=i] \]
那么我们可以得到
\[ \delta_{i,j}\binom{k}{j}=(-1)^{j-i}\binom{k-i}{k-j} \]
然后你解出来就可以了,但是我们平常写起来其实应该不是这样的

注意到一个组合式
\[ \binom{k}{j}\binom{j}{i}=\binom{k}{i}\binom{k-i}{k-j} \]
这个证明方法也多,你拆开或者组合意义理解都行


\[ \binom{k}{i}\sum_{j=i}^k(-1)^{j-i}\binom{k-i}{k-j}=[k=i] \]
就是把这个加到前面并不会影响什么

于是我们有
\[ \delta_{i,j}=(-1)^{j-i}\binom{j}{i} \]
综上
\[ B_i=\sum_{j=i}^n(-1)^{j-i}\binom{j}{i}A_j \]


Code:

#include <cstdio>
#include <cctype>
#include <algorithm>
using std::min;
const int SIZE=1<<21;
char ibuf[SIZE],*iS,*iT;
//#define gc() (iS==iT?(iT=(iS=ibuf)+fread(ibuf,1,SIZE,stdin),iS==iT?EOF:*iS++):*iS++)
#define gc() getchar()
template <class T>
void read(T &x)
{
    x=0;char c=gc();
    while(!isdigit(c)) c=gc();
    while(isdigit(c)) x=x*10+c-'0',c=gc();
}
const int mod=998244353;
int inline add(int x,int y){return x+y>=mod?x+y-mod:x+y;}
#define mul(x,y) (1ll*(x)*(y)%mod)
int qp(int d,int k){int f=1;while(k){if(k&1)f=mul(f,d);d=mul(d,d),k>>=1;}return f;}
const int N=5e6+1;
int fac[N],inv[N],dp[N],f[N],g[N],invg[N],yuy[N];
int C(int m,int n){return mul(mul(fac[m],inv[n]),inv[m-n]);}
int main()
{
    fac[0]=1;for(int i=1;i<N;i++) fac[i]=mul(fac[i-1],i);
    inv[N-1]=qp(fac[N-1],mod-2);
    for(int i=N-2;~i;i--) inv[i]=mul(inv[i+1],i+1);
    int T,n,m,l,k;read(T);
    while(T--)
    {
        read(n),read(m),read(l),read(k);
        int mi=min(n,min(m,l));
        if(k>mi)
        {
            puts("0");
            continue;
        }
        f[0]=1;
        for(int i=0;i<mi;i++) f[i+1]=mul(f[i],yuy[i]=mul(n-i,mul(m-i,l-i)));
        int fg=1,tot=yuy[0];
        yuy[mi]=0;
        for(int i=1;i<=mi;i++)
        {
            g[i]=add(tot,mod-yuy[i]);
            fg=mul(fg,g[i]);
        }
        invg[mi]=qp(fg,mod-2);
        for(int i=mi-1;~i;i--) invg[i]=mul(invg[i+1],g[i+1]);
        for(int i=1;i<=mi;i++) dp[i]=mul(f[i],invg[i]);
        int ans=0;
        for(int i=k;i<=mi;i++)
        {
            if(i-k&1) ans=add(ans,mod-mul(C(i,k),dp[i]));
            else ans=add(ans,mul(C(i,k),dp[i]));
        }
        printf("%d\n",ans);
    }
    return 0;
}

2019.5.20

标签:int,sum,CTS2019,CTSC2019,delta,立方体,binom,我们,dp
来源: https://www.cnblogs.com/butterflydew/p/10895448.html