WA 50pts FFT求调,悬关

P4245 【模板】任意模数多项式乘法

Xuan104_WA @ 2025-01-10 19:47:26

rt,提交记录

#include<bits/stdc++.h>
using namespace std;
#define int long long
const double pai=acos(-1.0);
const int N=400005,M=32768;
struct CC {
    double a,b;
    CC(){}
    CC(double a,double b):a(a),b(b){}
    CC operator + (CC i)const{return (CC){a+i.a,b+i.b};}
    CC operator - (CC i)const{return (CC){a-i.a,b-i.b}; }
    CC operator * (CC i)const{return (CC){a*i.a-b*i.b,a*i.b+b*i.a}; }
}A[N],B[N],C[N],D[N],E[N],F[N],G[N],H[N];
int f[N],g[N];
int n,m,mod,L,r[N],O[N];
void fft(CC *A,int lim,int opt){
    for(int i=0;i<lim;i++)if(i<r[i])swap(A[i],A[r[i]]);
    for(int mid=1;mid<lim;mid<<=1){
        CC w=CC(cos(pai/mid),opt*sin(pai/mid));

        for(int i=0;i<lim;i+=mid<<1){
            CC p=CC(1,0);
            for(int j=0;j<mid;j++,p=p*w){
                CC u=A[i+j],v=p*A[i+mid+j];
                A[i+j]=u+v;
                A[i+mid+j]=u-v;
            }
        }
    }
}
signed main(){
//  freopen("P4245_11.in","r",stdin);
//  freopen("test.out","w",stdout);
    cin>>n>>m>>mod;
    for(int i=0;i<=n;i++){
        cin>>f[i];f[i]%=mod;
        A[i]=CC(f[i]/M,0);
        B[i]=CC(f[i]%M,0);
    }
    for(int i=0;i<=m;i++){
        cin>>g[i];g[i]%=mod;
        C[i]=CC(g[i]/M,0);
        D[i]=CC(g[i]%M,0);
    }
    int lim=1;
    while(lim<=n+m)lim<<=1,L++;
    for(int i=0;i<lim;i++)r[i]=(r[i>>1]>>1|((i&1)<<(L-1)));

    fft(A,lim,1);fft(B,lim,1);fft(C,lim,1);fft(D,lim,1);
    for(int i=0;i<=lim;i++)E[i]=A[i]*C[i],F[i]=B[i]*C[i],G[i]=A[i]*D[i],H[i]=B[i]*D[i];
    fft(E,lim,-1);fft(F,lim,-1);fft(G,lim,-1);fft(H,lim,-1);
    for(int i=0;i<=n+m;i++)
        cout<<((int)(E[i].a/lim+0.5)%mod*M%mod*M%mod+(int)(F[i].a/lim+0.5)%mod*M%mod+(int)(G[i].a/lim+0.5)%mod*M%mod+(int)(H[i].a/lim+0.5)%mod)%mod<<" ";
    return 0;
}

by Xuan104_WA @ 2025-01-10 21:26:12

此贴结,原因是精度被卡了。在此警示后人:

不要用 double!!!!!!!

用 long double!!!!!!!


|