2 条题解

  • 0
    @ 2025-4-11 19:14:21

    注意不要爆int或long long 附上一份正解代码对拍使用

    ```
    #include<bits/stdc++.h>
    using namespace std;
    const int N=5e6+5;
    typedef long long ll;
    int mod;ll n;
    int down(const int&x){
        if(x>=mod)return x-mod;
        return x;
    }
    struct Modint{
        int v;
        Modint(int x=0){v=x;}
        Modint operator+(const Modint&x)const{return down(v+x.v);}
        Modint operator-(const Modint&x)const{return down(v+mod-x.v);}
        Modint operator*(const Modint&x)const{return 1ll*v*x.v%mod;}
        Modint operator=(const Modint&x){return v=x.v;}
        void operator+=(const Modint&x){v=down(v+x.v);}
        void operator-=(const Modint&x){v=down(v+mod-x.v);}
        void operator*=(const Modint&x){v=1ll*v*x.v%mod;}
    };
    struct Complex{
        Modint re,im;
        Complex(Modint x=0,Modint y=0){re=x,im=y;}
        Complex(int x,int y){re=x,im=y;}
        Complex operator+(const Complex&x)const{return Complex(re+x.re,im+x.im);}
        Complex operator-(const Complex&x)const{return Complex(re-x.re,im-x.im);}
        Complex operator*(const Complex&x)const{return Complex(re*x.re-im*x.im,re*x.im+im*x.re);}
        Complex operator=(const Complex&x){re=x.re,im=x.im;return *this;}
        void operator+=(const Complex&x){re+=x.re,im+=x.im;}
        void operator-=(const Complex&x){re-=x.re,im-=x.im;}
        void operator*=(const Complex&x){*this=*this*x;}
        int Im()const{return im.v;}
        int Re()const{return re.v;}
    }ans;
    typedef long long ll;
    ll calc(int a,int b,int c,int n){
        if(!a)return 1ll*b/c*(n+1);
        if(a>=c||b>=c)return 1ll*n*(n+1)/2*(a/c)+1ll*(n+1)*(b/c)+calc(a%c,b%c,c,n);
        ll m=(1ll*a*n+b)/c;return 1ll*n*m-calc(c,c-b-1,a,m-1);
    }
    namespace Find_Yuangeng{
        const int MAXN=N;
        int t,p,cnt,tot,ctans,fc[MAXN],ans[MAXN],pri[MAXN],rt[MAXN],q[MAXN],phi[MAXN];
        void init () {
            phi[1]=1;
            for (int i=2;i<=MAXN-5;i++) {
                if (!q[i]) {pri[++tot]=i,phi[i]=i-1;}
                for (int j=1;j<=tot&&pri[j]*i<=MAXN-10;j++) {
                    q[i*pri[j]]=1;
                    if (i%pri[j]==0) {
                        phi[i*pri[j]]=phi[i]*pri[j];
                        break;
                    }
                    phi[i*pri[j]]=phi[i]*(pri[j]-1);
                }
            }
            return;
        }
        int qpow (int a,int b,int p) {
            int res=1;
            while (b) {
                if (b&1) {res=(1ll*res*a)%p;}
                a=(1ll*a*a)%p;
                b>>=1;
            }
            return res;
        }
        bool chk (int x,int p) {
            if (qpow(x,phi[p],p)!=1) {return 0;}
            for (int i=1;i<=cnt;i++) {
                if (qpow(x,phi[p]/fc[i],p)==1) {return 0;}
            }
            return 1;
        }
        void proc (int p) {
            for (int i=2;i*i<=p;i++) {
                if (p%i==0) {
                    fc[++cnt]=i;
                    while (p%i==0) {p/=i;}
                }
            }
            if (p>1) {fc[++cnt]=p;}
            return;
        }
        int findrt (int p) {
            ctans=cnt=0;
            proc(phi[p]);
            for (int i=1;i<p;i++) {
                if (chk(i,p)) {return i;}
            }
            return 0;
        }
    }
    int g;
    int val[N],pw[N];
    int qpow(int a,int b){
        a%=mod;
        if(!a)return 0;
        return pw[1ll*val[a]*b%(mod-1)];
    }
    int inv(int x){
        return qpow(x,mod-2);
    }
    ll solve(int k,int m){
        ll ans=((inv(k)*m%mod)<=m);ans+=m;
        ans+=calc(k,0,mod,m);
        ans-=calc(k,mod-m,mod,m);
        return ans%(mod-1);
    }
    int main(){
        Find_Yuangeng::init();
        scanf("%d%lld",&mod,&n);
        if(mod%4==1&&n>=mod){
            puts("0 0");
            return 0;
        }
        g=Find_Yuangeng::findrt(mod);
        val[1]=0;pw[0]=1;
        for(int i=1;i<mod-1;i++){
            pw[i]=1ll*pw[i-1]*g%mod;
    		val[pw[i]]=i;
        }
        ll lim=n/mod,mul=1ll,m=n-lim*mod;
        for(int i=1;i<=m;i++)mul=4ll*mul*i*i%mod;
        mul=qpow(mul,lim%(mod-1));int t=lim*m%4;
        ans.re=mul,ans.im=0;
        for(int i=0;i<t;i++)ans*=Complex(0,1);
        for(int i=1;i<=m;i++)ans*=Complex(0,1ll*i*i%mod);
        if(m){
            ll nw_mul=1;
            for(int i=1;i<=m;i++)nw_mul=1ll*nw_mul*i%mod;
            nw_mul=qpow(nw_mul,m);
            ans*=Complex(nw_mul,0);
            for(int i=1;i<=m;i++)ans*=Complex(1,1);
            //(1+i)^m
            for(int i=2;i<mod-1;i++)if(inv(i)>i){
                int x=inv(i),val=solve(i,m);
                ans*=Complex(qpow(x+i,val),0);
                for(int i=0;i<val%4;i++)ans*=Complex(0,1);
            }
            int val=solve(mod-1,m);
            for(int i=1;i<=val;i++)ans*=Complex(1,mod-1);
        }
        printf("%d %d\n",ans.Re(),ans.Im());
        return 0;
    }
    ```
    

    信息

    ID
    564
    时间
    5000ms
    内存
    1024MiB
    难度
    10
    标签
    (无)
    递交数
    89
    已通过
    3
    上传者