zoukankan      html  css  js  c++  java
  • steins;Gate

    题意

    (n)个数(a_1,a_2,dots,a_n)。对于每一个(a_k),求有多少个有序二元组((i,j))满足((a_i * a_j) mod(P) = a_k),其中(P)为一给定质数。

    (1 le N le 200000,2 le Ple 200000,0 le a_ile2100000000)

    符号

    g :(P)的原根

    题解

    因为(a_i mod P = g^t,(0 < t < P )),实际上转换成([ 0, P - 1))要方便很多。所以((a_i * a_j) mod(P) = ((a_i mod P) * (a_j mod P) mod(P)) = g^{t_1+t_2} mod (P) = a_k)。将乘法变成了加法,(FFT)就能用上了,和(hdu4609)的处理方法是一样的,kuangbin聚聚写的很清楚,也算是一个套路了。为什么要把模(P)等于0的数扣出来,因为这样的数是不能用原根表示的。

    代码

    const int N = 600010;
    
    struct Complex {
        double r,i;
        Complex(double real=0.0,double image=0.0) {
            r=real;
            i=image;
        }
        Complex operator +(const Complex o){return Complex(r+o.r,i+o.i);}
        Complex operator -(const Complex o){return Complex(r-o.r,i-o.i);}
        Complex operator *(const Complex o){return Complex(r*o.r-i*o.i,r*o.i+i*o.r);}
    } b[N];
    
    int rev(int id, int len) {
        int pos = 0;
        for (int i = 0; (1 << i) < len; ++i) {
            pos <<= 1;
            if (id & (1 << i)) pos |= 1;
        }
        return pos;
    }
    
    Complex A[N];
    
    void FFT(Complex *a, int len, int DFT) {
        rep(i, 0, len) A[rev(i, len)] = a[i];
        for (int s = 1; (1 << s) <= len; ++s) {
            int m = (1 << s);
            Complex wm = Complex(cos(DFT * 2 * PI / m), sin(DFT * 2 * PI / m));
            for (int i = 0; i < len; i += m) {
                Complex w = Complex(1, 0);
                for (int j = 0; j < (m >> 1); ++j) {
                    Complex t = A[i + j];
                    Complex u = w * A[i + j + (m >> 1)];
                    A[i + j] = t + u;
                    A[i + j + (m >> 1)] = t - u;
                    w = w * wm;
                }
            }
        }
        if (DFT == -1) rep(i, 0, len) A[i].r /= len, A[i].i /= len;
        rep(i, 0, len) a[i] = A[i];
    }
    
    int n, g, P;
    int a[N], id[N];
    
    LL ans[N];
    
    bool check(int g) {
        LL t = 1;
        rep(i, 1, P - 1) {
            t = t * g % P;
            if (t == 1) return 0;
        }
        return 1;
    }
    
    int qpow(int x, int y) {
        int res = 1;
        for (; y; x = 1ll * x * x % P, y >>= 1) if (y & 1) res = 1ll * res * x % P;
        return res;
    }
    
    int main()
    {
        sc(n), sc(P);
        for (int i = 2; ; ++i) if (check(i)) {
            g = i;
            break;
        }
    
        LL t = 1;
        rep(i, 1, P) {
            t = t * g % P;
            id[t] = i;
        }
    
        t = 0;
        Rep(i, 1, n) {
            sc(a[i]);
            if (a[i] % P == 0) t++;
            else b[id[a[i] % P]].r++;
        }
    
        int len = (1 << 19);
    
        FFT(b, len, 1);
        rep(i, 0, len) b[i] = b[i] * b[i];
        FFT(b, len, -1);
    
        // 当P = 2时,i = 0也有贡献
        rep(i, 0, len) ans[qpow(g, i)] += (LL)(b[i].r + 0.5);
    
        Rep(i, 1, n) {
            if (a[i] >= P) printf("0
    ");
            else if (a[i] == 0) printf("%lld
    ", t * t + 2 * t * (n - t));
            else printf("%lld
    ", ans[a[i]]);
        }
    
        return 0;
    }
    
    
  • 相关阅读:
    Windows10 + eclipse + JDK1.8 + Apache Maven 3.6.0 + dl4j深度学习环境配置
    vector,deque,list的区别和使用
    extern C的用法解析
    向jupyter notebook加入Anaconda3中已添加的虚拟环境kernel
    TensorFlow学习
    windows10+Python3.6+Anaconda3+tensorflow1.10.0配置和安装
    torchvision
    无oracle客户端仅用plsql连接远程oracle
    poj 3463 Sightseeing(次短路+条数统计)
    10.11 noip模拟试题
  • 原文地址:https://www.cnblogs.com/zgglj-com/p/9749041.html
Copyright © 2011-2022 走看看