Pollard-rho(大整数质因子分解)

vector<ll> fac;
ll quick_mult(ll a, ll b, ll mod) {
    ll ans = 0;
    while(b) {
        if(b & 1) ans = (ans + a) % mod;
        a = (a + a) % mod;
        b >>= 1;
    }
    return ans;
}
ll quick_pow(ll a, ll n, ll mod) {
    ll ans = 1;
    while(n) {
        if(n & 1) ans = quick_mult(ans, a, mod);
        a = quick_mult(a, a, mod);
        n >>= 1;
    }
    return ans;
}
bool miller_rabin(ll n) {
    if(n == 2) return true;
    if(n < 2 || !(n & 1)) return false;
    ll s = 0, d = n - 1;
    while(!(d & 1)) {
        d >>= 1;
        s++;
    }
    for(int i = 1; i <= 11; i++) {
        ll a = rand() % (n - 2) + 2;
        ll now = quick_pow(a, d, n), pre = now;
        for(int j = 1; j <= s; j++) {
            now = quick_mult(now, now, n);
            if(now == 1 && pre != 1 && pre != n - 1) return false;
            pre = now;
        }
        if(now != 1) return false;
    }
    return true;
}
ll pollard_rho(ll n, int c) {
    ll x, y, i = 1, k = 2;
    x = y = rand() % (n - 2) + 2;
    for( ; ; ) {
        i++;
        x = (quick_mult(x, x, n) + c) % n;
        ll g = __gcd(y - x, n);
        if(g > 1 && g < n) return g;
        if(x == y) return n;
        if(i == k) y = x, k <<= 1;
    }
}
void find_fac(ll n) { //调用此函数,因子保存在fac中
    if(n == 1) return ;
    if(miller_rabin(n)) {
        fac.push_back(n);
        return;
    }
    ll p = n;
    int c = 1111;
    while(p >= n) p = pollard_rho(p, c--);
    find_fac(p);
    find_fac(n / p);
}
上一篇:[NOI2019] 斗主地


下一篇:量子力学基础-7