• LOJ #6261 一个人的高三楼


    生成函数和组合数学的灵活应用

    LOJ #6261

    题意:求一个数列的$ k$次前缀和


    $ Solution:$

    我们对原数列$ a$建生成函数$ A=sumlimits_{i=0}^{n-1} a_ix^i $

    求一次前缀和相当于将$ A$卷上生成函数$ B=sumlimits_{i=0}^{n-1}x^i pmod{x^n}$

    即我们要求的就是$ A·B^{k-1} pmod{x^n}$

    直接快速幂是$ log^2$的,但是生成函数$ B$有一些巧妙的性质:

    $ B^k(x)$的意义是选$ k$个自然数使得和为$ x$

    可以通过插板法得知$ B^k(x)$=$ C_{x+k}^x$

    然后求出$ A,B$之后$ NTT$卷积即可

    时间复杂度:$ O(n log n)$


     $ my code:$

    #include<ctime>
    #include<cmath>
    #include<cstdio>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    #include<queue>
    #define p 998244353 
    #define rt register int
    #define ll long long
    using namespace std;
    inline ll read(){
        ll x = 0; char zf = 1; char ch = getchar();
        while (ch != '-' && !isdigit(ch)) ch = getchar();
        if (ch == '-') zf = -1, ch = getchar();
        while (isdigit(ch)) x = x * 10 + ch - '0', ch = getchar(); return x * zf;
    }
    void write(ll y){if(y<0)putchar('-'),y=-y;if(y>9)write(y/10);putchar(y%10+48);}
    void writeln(const ll y){write(y);putchar('
    ');}
    int i,j,k,n,x,y,z,cnt,lim,m;
    vector<int>A,B,R;
    int inv[100010];
    int ksm(int x,int y){
        int ans=1;
        for(rt i=y;i;i>>=1,x=1ll*x*x%p)if(i&1)ans=1ll*ans*x%p;
        return ans;
    }
    void init(){
        lim=1;while(lim<=n+n)lim*=2;
        A.resize(lim);B.resize(lim);R.resize(lim);
        for(rt i=1;i<lim;i++)R[i]=(R[i>>1]>>1)|(i&1)*(lim>>1);
        for(rt i=0;i<n;i++)A[i]=read();
        inv[0]=inv[1]=1;B[0]=1;
        for(rt i=2;i<=n;i++)inv[i]=1ll*inv[p%i]*(p-p/i)%p;
        for(rt i=1;i<n;i++)B[i]=1ll*(i+m)*B[i-1]%p*inv[i]%p;
    }
    void NTT(int n,vector<int>&A,int fla){
        for(rt i=0;i<n;i++)if(i>R[i])swap(A[i],A[R[i]]);
        for(rt i=1;i<n;i<<=1){
            int w=ksm(3,(p-1)/2/i);
            for(rt j=0;j<n;j+=i<<1){
                int K=1;
                for(rt k=0;k<i;k++,K=1ll*K*w%p){
                    int x=A[j+k],y=1ll*K*A[i+j+k]%p;
                    A[j+k]=(x+y)%p,A[i+j+k]=(x-y)%p;
                }
            }
        }
        if(fla==-1){
            reverse(A.begin()+1,A.end());int invn=ksm(n,p-2);
            for(rt i=0;i<n;i++)A[i]=1ll*A[i]*invn%p;    
        }
    }
    int main(){
        n=read();m=(read()-1)%p;init();
        NTT(lim,A,1);NTT(lim,B,1);
        for(rt i=0;i<lim;i++)A[i]=1ll*A[i]*B[i]%p;
        NTT(lim,A,-1);
        for(rt i=0;i<n;i++)writeln((A[i]+p)%p);
        return 0;
    }
  • 相关阅读:
    Bootstrap 2.2.2 的新特性
    Apache POI 3.9 发布,性能显著提升
    SQL Relay 0.48 发布,数据库中继器
    ProjectForge 4.2.0 发布,项目管理系统
    红帽企业 Linux 发布 6.4 Beta 版本
    红薯 快速的 MySQL 本地和远程密码破解
    MariaDB 宣布成立基金会
    Percona XtraBackup 2.0.4 发布
    Rocks 6.1 发布,光盘机群解决方案
    精通Servlet研究,HttpServlet的实现追究
  • 原文地址:https://www.cnblogs.com/DreamlessDreams/p/10056752.html
Copyright © 2020-2023  润新知