【BZOJ 3884】 上帝与集合的正确用法

【题目链接】

           点击打开链接

【算法】

          通过欧拉拓展定理,列出递推公式

 【代码】

             

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;

ll T,N;
map<ll,ll> M;

template <typename T> inline void read(T &x) {
        ll f = 1; x = 0;
        char c = getchar();
        for    (; !isdigit(c); c = getchar()) { if (c == '-') f = -f; }
        for (; isdigit(c); c = getchar()) x = (x << 3) + (x << 1) + c - '0';
        x *= f;
}
template <typename T> inline void write(T x) {
        if (x < 0) { putchar('-'); x = -x; }    
        if (x > 9) write(x/10);
        putchar(x%10+'0'); 
}
template <typename T> inline void writeln(T x) {
        write(x);
        puts("");    
}

ll power(ll a,ll n,ll P) {
        ll res;
        if (n == 0) return 1;
        if (n == 1) return a % P;
        res = power(a,n>>1,P);
        res = res * res % P;
        if (n & 1) res = res * a % P;
        return res;     
}

ll phi(ll x) {
        ll i,ret=x;
        for (i = 2; i <= sqrt(x); i++) {
                if (x % i == 0) {
                        while (x % i == 0) x /= i;
                        ret = ret / i * (i - 1);
                }
        }    
        if (x > 1) ret = ret / x * (x - 1);
        return ret; 
} 

inline ll calc(ll n) {
        if (M.count(n)) return M[n];
        return M[n] = power(2,calc(phi(n))+phi(n),n);     
}

int main() {
    
        M[1] = 0;
        read(T);
        while (T--) {
                read(N);
                writeln(calc(N));    
        }
        
        return 0;
}


       
原文地址:https://www.cnblogs.com/evenbao/p/9196393.html