「专题总结」多项式(STAGE 1)

这么难的专题居然只给了这么短时间。。。

然而在NC的教导之下还是有一定的收获的。

必须打广告:0123

附带一个垃圾博客:-1

按照习惯,堆砌结论而不加证明。

Section1 导数:

基本形式:$f'(x)=limlimits_{Delta x ightarrow 0}frac{f(x+Delta x)-f(x)}{Delta x}$

一次函数:$f(x)=ax+b ightarrow f'(x)=a$

幂函数:$f(x)=x^n ightarrow f'(x)=nx^{n-1}$

正弦函数:$limlimits_{x ightarrow 0}sin(x)=x $,得到$f(x)=sin(ax+b) ightarrow f'(x)=a cos(ax+b)$

余弦函数:$limlimits_{x ightarrow 0}cos(x)=1 $,得到$f(x)=cos(ax+b) ightarrow f'(x)=-a sin(ax+b)$

指数函数:$e=limlimits_{n ightarrow + infty} (1+ frac{1}{n})^n$,得到$f(x)=a^x ightarrow f'(x)=a^x ln   a$

  特别的,自然对数的指数函数:$f(x)=e^x ightarrow e^x$。即$e$可以无限求导。

对数函数:$f(x)=log_a x ightarrow f'(x)=frac{1}{xlna}$

  特别的,自然对数的对数函数:$f(x)=frac{1}{x}$

运算法则:加法,减法,常数乘法。

乘法:设$h(x)=f(x)g(x)$,有$h'(x)=f'(x)g(x)+f(x)g'(x)$

除法:设$h(x)=frac{f(x)}{g(x)}$ ,有$h'(x)=frac{f'(x)g(x)-g'(x)f(x)}{g^2(x)}$

复合函数:设$h(x)=f(g(x))$,有$h'(x)=f'(g(x))g'(x)$

逆运算——积分:

多项式不定积分:$F'(x)=f(x) ,f(x)=ax^k ightarrow F(x)=frac{a}{k+1} x^{k+1}$

Section2 导数在多项式的应用:

泰勒展开:$f(x)=sumlimits_{i=0}^{n}frac{f^{(i)}(x_0)(x-x_0)^i}{i!}$

麦克劳林公式:$f(x)=sumlimits_{i=0}^{n}frac{f^{(i)}(0)x^i}{i!}$,是泰勒展开在$x_0$取0时的特殊形式。

级数求和公式:运用泰勒展开,讲简单形式与和式相互转化。

例如《在美妙的数学王国中畅游》一题中,运用泰勒展开,讲难以运算并求和的sin和exp函数都可以展开为多项式。

而多项式是可以直接相加的与自变量x无关,所以就可以用数据结构维护系数。

$e^x=sumlimits_{i=0}^{infty} frac{x^i}{i!}$

$frac{1}{1-x}=sumlimits_{i=0}^{infty} x^i$

$frac{1}{1+x}=sumlimits_{i=0}^{infty} (-x)^i$

$ln(1+x)= - sumlimits_{i=1}^{infty} frac{(-x)^i}{i} $

$sin(x)=sumlimits_{i=0}^{infty} (-1)^{i+1} imes frac{x^{2i-1}}{(2i-1)!}$

$cos(x)=sumlimits_{i=0}^{infty} (-1)^i imes frac{x^{2i}}{(2i)!}$

牛顿迭代:利用泰勒展开逼近函数零点。

多项式牛顿迭代:

若已经求出$G_0(x)$,使$F(G_0(x)) equiv 0(mod x^n)$,

则设$G(x) equiv G_0(x)-frac{F(G_0(x))}{F'(G_0(x))}(mod x^{2n})$,

有$F(G(x)) equiv 0 (mod x^{2n})$

迭代使精度翻倍。应用于多项式除法。

多项式全家桶:(洛谷题库搜索“多项式模板”)

模板区:

 1 #include<cstdio>
 2 #include<cmath>
 3 using namespace std;
 4 #define pi 3.141592653589793238462643383279
 5 #define S 262144
 6 #define mod 1000000007
 7 #define ll long long
 8 const int s=(1<<15)-1;
 9 struct cp{double r,i;
10     cp operator+(cp x){return (cp){r+x.r,i+x.i};}
11     cp operator-(cp x){return (cp){r-x.r,i-x.i};}
12     cp operator*(cp x){return (cp){r*x.r-i*x.i,x.r*i+r*x.i};}
13     void operator=(int a){r=a;i=0;}
14 }a1[S],a2[S],b1[S],b2[S],x2[S],x1[S],x0[S],o[2][19][S],R,X,Y;
15 int rev[S],n,A[S],inv[S],len=1,bit,a[S],b[S],c[S],d[S];
16 int pow(int b,int t,int a=1){for(;t;t>>=1,b=1ll*b*b%mod)if(t&1)a=1ll*a*b%mod;return a;}
17 ll r(cp x){return (ll)(floor(x.r+0.5))%mod;}
18 void FFT(cp *a,int opt){
19     for(int i=1;i<len;++i)rev[i]=rev[i>>1]>>1|(i&1?len>>1:0);
20     for(int i=1;i<len;++i)if(rev[i]>i)R=a[i],a[i]=a[rev[i]],a[rev[i]]=R;
21     for(int mid=1,p=0;mid<len;mid<<=1,p++)for(int i=0;i<len;i+=mid<<1)for(int j=i;j<i+mid;++j)
22         X=a[j],Y=a[j+mid]*o[opt>0][p][j-i],a[j]=X+Y,a[j+mid]=X-Y;
23     if(opt==-1)for(int i=0;i<len;++i)a[i].r/=len;
24 }
25 void MTT(int *a,int *b,int *c){
26     for(int i=0;i<len;++i)a1[i]=a[i]&s,a2[i]=a[i]>>15,b1[i]=b[i]&s,b2[i]=b[i]>>15;
27     FFT(a1,1);FFT(a2,1);FFT(b1,1);FFT(b2,1);
28     for(int i=0;i<len;++i)x2[i]=b2[i]*a2[i],x0[i]=b1[i]*a1[i],x1[i]=b2[i]*a1[i]+b1[i]*a2[i];
29     FFT(x2,-1);FFT(x1,-1);FFT(x0,-1);
30     for(int i=0;i<len;++i)c[i]=(((r(x2[i])<<30)+(r(x1[i])<<15)+r(x0[i]))%mod+mod)%mod;
31 }
32 void divide(int n){
33     if(n==1){inv[0]=pow(A[0],mod-2);return;}
34     divide(n+1>>1);len=1;while(len<n<<1)len<<=1;
35     for(int i=0;i<len;++i)a[i]=(i<n)*A[i],b[i]=inv[i]*(i<n+1>>1);
36     MTT(a,b,c);MTT(c,b,d);
37     for(int i=0;i<len;++i)inv[i]=(b[i]*2-d[i]+mod)%mod;
38 }
39 int main(){
40     scanf("%d",&n);
41     for(int i=0;i<n;++i)scanf("%d",&A[i]);
42     while(len<n<<1)len<<=1;
43     for(int i=0;1<<i<len;++i)for(int j=0;j<1<<i;++j)
44         o[0][i][j]=(cp){cos(pi/(1<<i)*j),sin(pi/(1<<i)*j)},
45         o[1][i][j]=(cp){cos(pi/(1<<i)*j),-sin(pi/(1<<i)*j)};
46     divide(n);for(int i=0;i<n;++i)printf("%d ",inv[i]);puts("");
47 }
求逆inv(加强:任意模数)
 1 #include<cstdio>
 2 #define int long long
 3 #define mod 998244353
 4 #define S 1<<20
 5 int rev[S],F[S],G[S],Q[S],n,m,len=1,ra[S],rb[S],iG[S],RA[S],RB[S];
 6 int pow(int b,int t,int a=1){for(;t;t>>=1,b=b*b%mod)if(t&1)a=a*b%mod;return a;}
 7 void NTT(int *a,int opt){
 8     for(int i=0;i<len;++i)rev[i]=rev[i>>1]>>1|(i&1?len>>1:0);
 9     for(int i=0;i<len;++i)if(rev[i]>i)a[i]^=a[rev[i]]^=a[i]^=a[rev[i]];
10     for(int mid=1;mid<len;mid<<=1)
11         for(int i=0,t=pow(3,(mod-1)/mid/2*opt+mod-1);i<len;i+=mid<<1)
12             for(int j=i,w=1,x,y;j<i+mid;++j,w=w*t%mod)
13                 x=a[j],y=a[j+mid]*w%mod,a[j]=(x+y)%mod,a[j+mid]=(x-y+mod)%mod;
14     if(opt==-1)for(int i=0,iv=pow(len,mod-2);i<len;++i)a[i]=a[i]*iv%mod;
15 }
16 void re(int *a,int n){for(int i=0,j=n-1;i<j;++i,--j)a[i]^=a[j]^=a[i]^=a[j];}
17 void pt(int *a,int n){for(int i=0;i<n;++i)printf("%lld ",a[i]);puts("");}
18 void mul(int *a,int la,int *b,int lb,int *c){
19     len=1;while(len<la+lb<<1)len<<=1;
20     for(int i=0;i<len;++i)ra[i]=rb[i]=0;
21     for(int i=0;i<la;++i)ra[i]=a[i];
22     for(int i=0;i<lb;++i)rb[i]=b[i];
23     NTT(ra,1);NTT(rb,1);
24     for(int i=0;i<len;++i)c[i]=ra[i]*rb[i]%mod;
25     NTT(c,-1);
26 }
27 void mul(int *a,int *b,int *c){
28     for(int i=0;i<len;++i)ra[i]=a[i],rb[i]=b[i];
29     NTT(ra,1);NTT(rb,1);
30     for(int i=0;i<len;++i)c[i]=ra[i]*rb[i]%mod;
31     NTT(c,-1);
32 }
33 void inv(int *a,int x,int *b){
34     if(x==1){b[0]=pow(a[0],mod-2);return;}
35     inv(a,x+1>>1,b);len=1;while(len<x<<1)len<<=1;
36     for(int i=0;i<len;++i)RA[i]=RB[i]=0;
37     for(int i=0;i<x;++i)RA[i]=a[i];
38     for(int i=0;i<x+1>>1;++i)RB[i]=b[i];
39     mul(RA,RB,RA);mul(RA,RB,RA);
40     for(int i=0;i<x;++i)b[i]=(RB[i]+RB[i]-RA[i]+mod)%mod;
41 }
42 main(){
43     scanf("%lld%lld",&n,&m);n++;m++;
44     for(int i=0;i<n;++i)scanf("%lld",&F[i]);
45     for(int i=0;i<m;++i)scanf("%lld",&G[i]);
46     re(F,n);re(G,m);inv(G,n-m+1,iG);mul(F,n,iG,n-m+1,Q);re(Q,n-m+1);pt(Q,n-m+1);
47     re(G,m);mul(Q,n-m+1,G,m,Q);re(F,n);
48     for(int i=0;i<m-1;++i)printf("%lld ",(F[i]-Q[i]+mod)%mod);puts("");
49 }
除法
 1 #include<cstdio>
 2 #include<map>
 3 using namespace std;
 4 map<int,int>M;
 5 #define mod 998244353
 6 #define S 1<<19
 7 int pow(int b,int t,int a=1){for(;t;t>>=1,b=1ll*b*b%mod)if(t&1)a=1ll*a*b%mod;return a;}
 8 int BSGS(int x){
 9     int k=pow(3,100000),I=pow(3,mod-2);
10     for(int i=0,p=1;i<mod;i+=100000,p=1ll*p*k%mod)M[p]=i;
11     for(int i=0,p=1;i<100000;++i,p=1ll*I*p%mod)if(M.find(1ll*x*p%mod)!=M.end())
12         return i+M[1ll*x*p%mod];
13 }
14 int rev[S],a[S],s[S],A[S],b[S],ra[S],rb[S],R[S],len,n,r[S];
15 #define mat len=1;while(len<n<<1)len<<=1
16 void NTT(int *a,int opt){
17     for(int i=0;i<len;++i)rev[i]=rev[i>>1]>>1|(i&1?len>>1:0);
18     for(int i=0;i<len;++i)if(rev[i]>i)a[i]^=a[rev[i]]^=a[i]^=a[rev[i]];
19     for(int mid=1;mid<len;mid<<=1)
20         for(int i=0,t=pow(3,(mod-1)/mid/2*opt+mod-1);i<len;i+=mid<<1)
21             for(int j=i,w=1,x,y;j<i+mid;++j,w=1ll*w*t%mod)
22                 x=a[j],y=1ll*a[j+mid]*w%mod,a[j]=(x+y)%mod,a[j+mid]=(x-y+mod)%mod;
23     if(opt==-1)for(int i=0,iv=pow(len,mod-2);i<len;++i)a[i]=1ll*a[i]*iv%mod;
24 }
25 void mul(int *a,int *b,int *c,int opt=1){
26     NTT(a,1);NTT(b,1);
27     for(int i=0;i<len;++i)c[i]=1ll*a[i]*b[i]%mod;
28     NTT(c,-1);if(opt)NTT(b,-1);
29 }
30 void inv(int n){
31     if(n==1){r[0]=pow(b[0],mod-2);return;}
32     inv(n+1>>1);mat;
33     for(int i=0;i<len;++i)ra[i]=i<n?b[i]:0,rb[i]=i<n+1>>1?r[i]:0;
34     mul(ra,rb,R);mul(R,rb,R);
35     for(int i=0;i<len;++i)r[i]=(0ll+rb[i]+rb[i]-R[i]+mod)%mod;
36 }
37 void sqr(int n){
38     if(n==1){s[0]=pow(3,BSGS(A[0])/2);if(s[0]>mod-s[0])s[0]=mod-s[0];return;}
39     sqr(n+1>>1);mat;
40     for(int i=0;i<len;++i)a[i]=i<n?A[i]:0,b[i]=i<n+1>>1?s[i]:0;
41     inv(len>>1);mat;for(int i=len>>1;i<len;++i)r[i]=0;
42     mul(a,r,R,0);for(int i=0;i<len;++i)s[i]=(b[i]+R[i])*499122177ll%mod;
43 }
44 int main(){
45     scanf("%d",&n);
46     for(int i=0;i<n;++i)scanf("%d",&A[i]);
47     sqr(n);
48     for(int i=0;i<n;++i)printf("%d ",s[i]);puts("");
49 }
开根sqr(加强:不保证a0=1)
 1 #include<cstdio>
 2 #define int long long
 3 #define mod 998244353
 4 #define S 1<<19
 5 int n,len,rev[S],A[S],iA[S],ra[S],rb[S],Ra[S],Rb[S],ans[S],l1[S],l2[S];
 6 int pow(int b,int t,int a=1){for(;t;t>>=1,b=b*b%mod)if(t&1)a=a*b%mod;return a;}
 7 void deriv(int *a,int n,int *b){for(int i=0;i<n-1;++i)b[i]=a[i+1]*(i+1)%mod;b[n-1]=0;}
 8 void integ(int *a,int n,int *b){for(int i=n-1;i;--i)b[i]=a[i-1]*pow(i,mod-2)%mod;b[0]=0;}
 9 void NTT(int *a,int opt){
10     for(int i=0;i<len;++i)rev[i]=rev[i>>1]>>1|(i&1?len>>1:0);
11     for(int i=0;i<len;++i)if(rev[i]>i)a[i]^=a[rev[i]]^=a[i]^=a[rev[i]];
12     for(int mid=1;mid<len;mid<<=1)
13         for(int i=0,t=pow(3,(mod-1)/mid/2*opt+mod-1);i<len;i+=mid<<1)
14             for(int j=i,w=1,x,y;j<i+mid;++j,w=w*t%mod)
15                 x=a[j],y=a[j+mid]*w%mod,a[j]=(x+y)%mod,a[j+mid]=(x-y+mod)%mod;
16     if(opt==-1)for(int i=0,iv=pow(len,mod-2);i<len;++i)a[i]=a[i]*iv%mod;
17 }
18 void pt(int *a,int n=len){for(int i=0;i<n;++i)printf("%lld ",a[i]);puts("");}
19 void mat(int x){len=1;while(len<x)len<<=1;}
20 void mul(int *a,int *b,int *c){
21     for(int i=0;i<len;++i)Ra[i]=a[i],Rb[i]=b[i];
22     NTT(Ra,1);NTT(Rb,1);for(int i=0;i<len;++i)c[i]=Ra[i]*Rb[i]%mod;NTT(c,-1);
23 }
24 void inv(int *a,int n,int *b){
25     if(n==1){b[0]=pow(a[0],mod-2);return;}
26     inv(a,n+1>>1,b);mat(n<<1);
27     for(int i=0;i<len;++i)ra[i]=rb[i]=0;
28     for(int i=0;i<n;++i)ra[i]=a[i];
29     for(int i=0;i<n+1>>1;++i)rb[i]=b[i];
30     mul(ra,rb,ra);mul(ra,rb,ra);
31     for(int i=0;i<n;++i)b[i]=(rb[i]+rb[i]-ra[i]+mod)%mod;
32 }
33 void ln(int *a,int *b,int n){inv(a,n,l1);deriv(a,n,l2);mat(n<<1);mul(l1,l2,b);integ(b,n,b);}
34 main(){
35     scanf("%lld",&n);
36     for(int i=0;i<n;++i)scanf("%lld",&A[i]);
37     ln(A,ans,n);
38     for(int i=0;i<n;++i)printf("%lld ",ans[i]);puts("");
39 }
自然对数ln
 1 #include<cstdio>
 2 #define int long long
 3 #define mod 998244353
 4 #define S 1<<19
 5 int rev[S],len,n,A[S],ans[S];
 6 int pow(int b,int t,int a=1){for(;t;t>>=1,b=b*b%mod)if(t&1)a=a*b%mod;return a;}
 7 void NTT(int *a,int opt){
 8     for(int i=0;i<len;++i)rev[i]=rev[i>>1]>>1|(i&1?len>>1:0);
 9     for(int i=0;i<len;++i)if(rev[i]>i)a[i]^=a[rev[i]]^=a[i]^=a[rev[i]];
10     for(int mid=1;mid<len;mid<<=1)
11         for(int i=0,t=pow(3,(mod-1)/mid/2*opt+mod-1);i<len;i+=mid<<1)
12             for(int j=i,w=1,x,y;j<i+mid;++j,w=w*t%mod)
13                 x=a[j],y=a[j+mid]*w%mod,a[j]=(x+y)%mod,a[j+mid]=(x-y+mod)%mod;
14     if(opt==-1)for(int i=0,iv=pow(len,mod-2);i<len;++i)a[i]=a[i]*iv%mod;
15 }
16 void pt(int *a,int n=len){for(int i=0;i<n;++i)printf("%lld ",a[i]);puts("");}
17 void mat(int x){len=1;while(len<x)len<<=1;}
18 void deriv(int *a,int n,int *b){for(int i=1;i<n;++i)b[i-1]=a[i]*i%mod;b[n-1]=0;}
19 void integ(int *a,int n,int *b){for(int i=1;i<n;++i)b[i]=a[i-1]*pow(i,mod-2)%mod;b[0]=0;}
20 int r1[S],r2[S];
21 void mul(int *a,int *b,int *c){
22     for(int i=0;i<len;++i)r1[i]=a[i],r2[i]=b[i];
23     NTT(r1,1);NTT(r2,1);for(int i=0;i<len;++i)c[i]=r1[i]*r2[i]%mod;NTT(c,-1);
24 }
25 int v1[S],v2[S];
26 void inv(int *a,int n,int *b){
27     if(n==1){b[0]=pow(a[0],mod-2);return;}
28     inv(a,n+1>>1,b);mat(n<<1);
29     for(int i=0;i<len;++i)v1[i]=v2[i]=0;
30     for(int i=0;i<n;++i)v1[i]=a[i];
31     for(int i=0;i<n+1>>1;++i)v2[i]=b[i];
32     mul(v1,v2,v1);mul(v1,v2,v1);
33     for(int i=0;i<n;++i)b[i]=(v2[i]+v2[i]-v1[i]+mod)%mod;
34 }
35 int n1[S],n2[S];
36 void ln(int *a,int n,int *b){deriv(a,n,n1);inv(a,n,n2);mat(n<<1);mul(n1,n2,n1);integ(n1,n,b);}
37 int e[S];
38 void exp(int *a,int n,int *b){
39     if(n==1){b[0]=1;return;}
40     exp(a,n+1>>1,b);ln(b,n,e);
41     for(int i=0;i<n;++i)e[i]=(a[i]-e[i]+mod)%mod;e[0]++;
42     mat(n<<1);mul(b,e,b);
43     for(int i=n;i<len;++i)b[i]=0;
44 }
45 main(){
46     scanf("%lld",&n);
47     for(int i=0;i<n;++i)scanf("%lld",&A[i]);
48     exp(A,n,ans);pt(ans,n);
49 }
自然对数幂exp
 1 #include<cstdio>
 2 #define int long long
 3 #define mod 998244353
 4 #define S 1<<20
 5 int rev[S],len,n,k,c,A[S],r1[S],r2[S],v1[S],v2[S],e[S],n1[S],n2[S],p[S],ans[S],I;
 6 int pow(int b,int t,int a=1){for(;t;t>>=1,b=b*b%mod)if(t&1)a=a*b%mod;return a;}
 7 void NTT(int*a,int opt){
 8     for(int i=0;i<len;++i)rev[i]=rev[i>>1]>>1|(i&1?len>>1:0);
 9     for(int i=0;i<len;++i)if(rev[i]>i)a[i]^=a[rev[i]]^=a[i]^=a[rev[i]];
10     for(int mid=1;mid<len;mid<<=1)
11         for(int i=0,t=pow(3,(mod-1)/mid/2*opt+mod-1);i<len;i+=mid<<1)
12             for(int j=i,x,y,w=1;j<i+mid;++j,w=w*t%mod)
13                 x=a[j],y=a[j+mid]*w%mod,a[j]=(x+y)%mod,a[j+mid]=(x-y+mod)%mod;
14     if(opt==-1)for(int i=0,iv=pow(len,mod-2);i<len;++i)a[i]=a[i]*iv%mod;
15 }
16 void pt(int*a,int n=len){for(int i=0;i<n;++i)printf("%lld ",a[i]);puts("");}
17 void mat(int x){len=1;while(len<x)len<<=1;}
18 void deriv(int*a,int n,int*b){for(int i=0;i<n;++i)b[i]=a[i+1]*(i+1)%mod;}
19 void integ(int*a,int n,int*b){for(int i=1;i<n;++i)b[i]=a[i-1]*pow(i,mod-2)%mod;b[0]=0;}
20 void mul(int*a,int*b,int*c){
21     for(int i=0;i<len;++i)r1[i]=a[i],r2[i]=b[i];
22     NTT(r1,1);NTT(r2,1);for(int i=0;i<len;++i)c[i]=r1[i]*r2[i]%mod;NTT(c,-1);
23 }
24 void inv(int*a,int n,int*b){
25     if(n==1){b[0]=pow(a[0],mod-2);return;}
26     inv(a,n+1>>1,b);mat(n<<1);
27     for(int i=0;i<len;++i)v1[i]=v2[i]=0;
28     for(int i=0;i<n;++i)v1[i]=a[i];
29     for(int i=0;i<n+1>>1;++i)v2[i]=b[i];
30     mul(v1,v2,v1);mul(v1,v2,v1);
31     for(int i=0;i<n;++i)b[i]=(v2[i]+v2[i]-v1[i]+mod)%mod;
32 }
33 void ln(int*a,int n,int*b){
34     deriv(a,n,n1);inv(a,n,n2);mat(n<<1);
35     for(int i=n;i<len;++i)n1[i]=n2[i]=0;
36     mul(n1,n2,n1);integ(n1,n,b);
37 }
38 void exp(int*a,int n,int*b){
39     if(n==1){b[0]=1;return;}
40     exp(a,n+1>>1,b);ln(b,n,e);
41     for(int i=0;i<n;++i)e[i]=(a[i]-e[i]+mod)%mod;e[0]++;
42     mat(n<<1);for(int i=n;i<len;++i)e[i]=0;mul(e,b,b);
43 }
44 void pow(int*a,int n,int*b,int k){ln(a,n,p);for(int i=0;i<n;++i)p[i]=p[i]*k%mod;exp(p,n,b);}
45 main(){
46     scanf("%lld%lld",&n,&k);
47     for(int i=0,x=1;i<n;++i)scanf("%lld",&A[i-c]),x*=(!A[i-c]),c+=x;
48     I=pow(A[0],mod-2);for(int i=0;i<n-c;++i)A[i]=A[i]*I%mod;pow(A,n-c,ans,k);
49     I=pow(I,(mod-2)*k);for(int i=0;i<n-c;++i)ans[i]=ans[i]*I%mod;
50     for(int i=0;i<c*k&&i<n;++i)printf("0 ");
51     for(int i=0;i<n-c*k;++i)printf("%lld ",ans[i]);puts("");
52 }
快速幂pow(加强:不保证a0=1)

Section 3:各种卷积性变换

FFT:运用复数单位根进行插值变换

NTT:运用原根进行插值变换

FWT:运用位运算卷积(与/或/异或)

MTT:任意模数NTT

 1 #include<cstdio>
 2 #define int long long
 3 #define S 262144
 4 #define m1 167772161
 5 #define m2 998244353
 6 #define m3 1004535809
 7 const int M=1ll*m1*m2,R=m2%m1;
 8 int mod,len=1,rev[S],a[S],b[S],ra[S],rb[S],ans[3][S],n,m,p,c;
 9 int pow(int b,int t,int m,int a=1){for(;t;t>>=1,b=b*b%m)if(t&1)a=a*b%m;return a;}
10 int mul(int x,int y,int a=0){for(;y;y>>=1,x=(x+x)%M)if(y&1)a=(a+x)%M;return a;}
11 void NTT(int *a,int opt){
12     for(int i=1;i<len;++i)if(rev[i]>i)a[i]^=a[rev[i]]^=a[i]^=a[rev[i]];
13     for(int mid=1;mid<len;mid<<=1)
14         for(int i=0,t=pow(3,(mod-1)/2/mid*opt+mod-1,mod);i<len;i+=mid<<1)
15             for(int j=i,w=1,x,y;j<i+mid;++j,w=w*t%mod)
16                 x=a[j],y=a[j+mid]*w%mod,a[j]=(x+y)%mod,a[j+mid]=(x-y+mod)%mod;
17     if(opt==-1)for(int i=0,iv=pow(len,mod-2,mod);i<len;++i)a[i]=a[i]*iv%mod;
18 }
19 void solve(int x){mod=x;
20     for(int i=0;i<len;++i)a[i]=ra[i],b[i]=rb[i];
21     NTT(a,1);NTT(b,1);
22     for(int i=0;i<len;++i)ans[c][i]=a[i]*b[i]%mod;
23     NTT(ans[c],-1);c++;
24 }
25 int cal(int a,int b,int c){
26     int x=((mul(a*m2%M,pow(R,m1-2,m1)))+mul(b*m1%M,pow(m1,m2-2,m2)))%M;
27     int y=((c-x)%m3+m3)%m3*pow(M%m3,m3-2,m3)%m3%p;return (M%p*y+x)%p;
28 }
29 main(){
30     scanf("%lld%lld%lld",&n,&m,&p);
31     for(int i=0;i<=n;++i)scanf("%lld",&ra[i]);
32     for(int i=0;i<=m;++i)scanf("%lld",&rb[i]);
33     while(len<=n+m+1)len<<=1;
34     for(int i=1;i<len;++i)rev[i]=rev[i>>1]>>1|(i&1?len>>1:0);
35     solve(m1);solve(m2);solve(m3);
36     for(int i=0;i<=n+m;++i)printf("%lld ",cal(ans[0][i],ans[1][i],ans[2][i]));
37 }
三模数NTT->MTT
 1 #include<cstdio>
 2 #include<cmath>
 3 using namespace std;
 4 #define pi 3.141592653589793238462643383279
 5 #define S 262144
 6 #define mod 1000000007
 7 #define ll long long
 8 const int s=(1<<15)-1;
 9 struct cp{double r,i;
10     cp operator+(cp x){return (cp){r+x.r,i+x.i};}
11     cp operator-(cp x){return (cp){r-x.r,i-x.i};}
12     cp operator*(cp x){return (cp){r*x.r-i*x.i,x.r*i+r*x.i};}
13     void operator=(int a){r=a;i=0;}
14 }a1[S],a2[S],b1[S],b2[S],o[2][19][S],X,Y,A1,A2,B1,B2;
15 int rev[S],n,A[S],inv[S],len=1,bit,a[S],b[S],c[S];
16 int pow(int b,int t,int a=1){for(;t;t>>=1,b=1ll*b*b%mod)if(t&1)a=1ll*a*b%mod;return a;}
17 ll r(cp x){return (ll)(floor(x.r+0.5))%mod;}
18 void FFT(cp *a,int opt){
19     for(int i=1;i<len;++i)rev[i]=rev[i>>1]>>1|(i&1?len>>1:0);
20     for(int i=1;i<len;++i)if(rev[i]>i)X=a[i],a[i]=a[rev[i]],a[rev[i]]=X;
21     for(int mid=1,p=0;mid<len;mid<<=1,p++)for(int i=0;i<len;i+=mid<<1)for(int j=i;j<i+mid;++j)
22         X=a[j],Y=a[j+mid]*o[opt>0][p][j-i],a[j]=X+Y,a[j+mid]=X-Y;
23     if(opt==-1)for(int i=0;i<len;++i)a[i].r/=len;
24 }
25 void MTT(int *a,int *b,int *c){
26     for(int i=0;i<len;++i)a1[i]=a[i]&s,a2[i]=a[i]>>15,b1[i]=b[i]&s,b2[i]=b[i]>>15;
27     FFT(a1,1);FFT(a2,1);FFT(b1,1);FFT(b2,1);
28     for(int i=0;i<len;++i)A1=a1[i],B1=b1[i],A2=a2[i],B2=b2[i],
29         a1[i]=B2*A2,a2[i]=B1*A1,b1[i]=B2*A1+B1*A2;
30     FFT(b1,-1);FFT(a2,-1);FFT(a1,-1);
31     for(int i=0;i<len;++i)c[i]=(((r(a1[i])<<30)+(r(b1[i])<<15)+r(a2[i]))%mod+mod)%mod;
32 }
33 void divide(int n){
34     if(n==1){inv[0]=pow(A[0],mod-2);return;}
35     divide(n+1>>1);len=1;while(len<n<<1)len<<=1;
36     for(int i=0;i<len;++i)a[i]=(i<n)*A[i],b[i]=inv[i]*(i<n+1>>1);
37     MTT(a,b,c);MTT(c,b,c);
38     for(int i=0;i<len;++i)inv[i]=(b[i]*2-c[i]+mod)%mod;
39 }
40 int main(){
41     scanf("%d",&n);
42     for(int i=0;i<n;++i)scanf("%d",&A[i]);
43     while(len<n<<1)len<<=1;
44     for(int i=0;1<<i<len;++i)for(int j=0;j<1<<i;++j)
45         o[0][i][j]=(cp){cos(pi/(1<<i)*j),sin(pi/(1<<i)*j)},
46         o[1][i][j]=(cp){cos(pi/(1<<i)*j),-sin(pi/(1<<i)*j)};
47     divide(n);for(int i=0;i<n;++i)printf("%d ",inv[i]);puts("");
48 }
拆系数MTT
1 for(int i=1;i<len;++i)for(int j=0;j<len;j+=i)for(int k=j;k<j+i;++k)a[k+i]+=a[k]*opt;//or
2 for(int i=1;i<len;++i)for(int j=0;j<len;j+=i)for(int k=j;k<j+i;++k)a[k]+=a[k+i]*opt;//and
3 for(int i=1;i<len;++i)for(int j=0;j<len;j+=i)for(int k=j;k<j+i;++k)
4     a[k]+=a[k+i],a[k+i]=a[k]-a[k+i]*2,a[k],a[k]/=(opt==-1?2:1),a[k+i]/=(opt==-1?2:1);//xor
FWT(or,and,xor)

Section 4:母函数

OGF:$F(x)=sumlimits_{i=0}^{infty}a_ix^i$。常用于组合。

EGF:$F(x)=sumlimits_{i=0}^{infty}frac{a_i}{i!}x^i$。常用于排列。

主要就是用于把数列带入需要化简的式子,以便于进行多项式运算。

原文地址:https://www.cnblogs.com/hzoi-DeepinC/p/12040042.html