CF 1528 F AmShZ Farm 题解

CF 1528 F AmShZ Farm 题解

考虑上面序列是好的:

可以用以下组合意义来理解:

\(n\)个物品,从\(1\)\(n\)放置,第\(i\)个物品放置的位置是\(a_i\)之后第一个空位(\(n\)的下一个是\(1\))。

序列是好的当且仅当,没有一个数字越过了\(n,1\)。考虑新添加一个位置\(n+1\),也就是说\(n+1\)最后必须为空。

所以好的序列个数为\((n+1)^n\)

枚举每一个数字的贡献:

\(\frac{1}{n+1}\sum_{i=0}^{n+1}(\sum_{cnt=0}^n{n\choose cnt} cnt^k (n)^{n-cnt})\)

=
\(\sum_{cnt=0}^n{n\choose cnt} cnt^k (n)^{n-cnt}\)

考虑内部式子的组合意义:从\(n\)个数字中选择\(cnt\)个,然后给\(k\)个数字选择一个之前选出的\(cnt\)中的数字中的一个,给剩下的\(n-cnt\)个数字写上\([1,n]\)的数字。

可以先分组然后再选择。

答案就是:

\(\sum_{i=1}^k s(k,i)\times n^{\underline{i}} \times(n+1)^{n-i}\)

\(s\)是斯特林数,计算一行的时间复杂度为\(O(k\log k)\)

int n,k;
int fact[100000+20];
int str[100000+20];
int main(){
    cin>>n>>k;
    fact[0]=1;
    rb(i,1,100000) fact[i]=1ll*fact[i-1]*i%MOD;
    vector<int> A(k+1,0),B(k+1,0);
    rb(i,0,k) A[i]=1ll*quick(i,k)*inv(fact[i])%MOD;
    rb(i,0,k) B[i]=1ll*(i%2? (MOD-1):1)*inv(fact[i])%MOD;
    A=A*B;
    rb(i,0,k) str[i]=A[i];
    int prod1=1;
    int answer=0;
    rb(i,1,min(k,n)){
        prod1=1ll*prod1*(n-i+1)%MOD;
        answer+=1ll*str[i]*prod1%MOD*quick(n+1,n-i)%MOD;
        answer%=MOD;
    }
    cout<<answer<<endl;
    return 0;
}
posted @ 2021-12-07 22:41  WWW~~~  阅读(35)  评论(0编辑  收藏  举报