提交时间:2024-01-02 17:37:45

运行 ID: 24561

#include <bits/stdc++.h> #define int long long #define endl "\n" using namespace std; const int M=998244353,G=3,iG=(M+1)/3; int rev[(1<<20)+10]; inline int qp(int a,int x){ int res=1; while(x){ if(x&1)res=res*a%M; a=a*a%M; x>>=1; } return res; } inline int inv(int x){return qp(x,M-2);} const int N=1<<20,IVN=inv(N),K=20; inline void NTT(int *f,int g){ for(int i=0;i<N;i++)if(rev[i]>i)swap(f[i],f[rev[i]]); for(int len=2;len<=N;len<<=1) for(int t=0,L=len/2,dwg=qp(g,(M-1)/len);t<N;t+=len) for(int j=t,buf=1;j<t+L;j++){ int a=f[j],b=f[j+L]*buf%M; f[j]=(a+b),f[j+L]=(a-b+M)%M; if(f[j]>=M)f[j]-=M; if(f[j+L]>=M)f[j+L]-=M; buf=buf*dwg%M; } if(g==iG)for(int i=0;i<N;i++)f[i]=f[i]*IVN%M; } inline void init(){for(int i=0;i<N;i++)if(i&1)rev[i]=(rev[i>>1]>>1)|(1<<K-1);else rev[i]=rev[i>>1]>>1;} int f[(1<<20)+10],g[(1<<20)+10]; int ANS[(1<<20)+10]; inline void TIMES(int *f,int *g){ NTT(f,G),NTT(g,G); for(int i=0;i<N;i++)ANS[i]=(ANS[i]+f[i]*g[i])%M; //NTT(f,iG),NTT(g,iG); memset(f,0,N*sizeof(int)); memset(g,0,N*sizeof(int)); } int n,m; vector<int>BG; int q[500400]; const int T=2; signed main(){ ios::sync_with_stdio(0); //freopen("a.in","r",stdin); //freopen("a.out","w",stdout); init(); cin>>n>>m; for(int i=1;i<=n;i++){ int x; cin>>x; q[x]++; } for(int i=1;i<=m;i++) if(q[i]>T) BG.push_back(i); for(int x=1;x<=T;x++){ //cout<<x<<" "; //cout.flush(); for(int i=1;i<=m;i++) f[i]=(x==q[i])*q[i],g[i]=(x<=q[i]); TIMES(f,g); for(int i=1;i<=m;i++) f[i]=(x==q[i])*q[i],g[i]=(x<q[i]); TIMES(f,g); } for(int i=0;i<N;i++) ANS[i]%=M; NTT(ANS,iG); for(int x:BG) for(int y:BG) ANS[x+y]+=min(q[x],q[y]); for(int i=1;i<=m;i++) cout<<ANS[i]/2<<" "; cout.flush(); return 0; }