[CodeForces - 906D] Power Tower——扩展欧拉定理
Posted lfri
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[CodeForces - 906D] Power Tower——扩展欧拉定理相关的知识,希望对你有一定的参考价值。
题意
给你 $n$ 个数 $w$ 和一个数 $p$,$q$个询问,每次询问一个区间 $[l,r] $,求 $w_l^(w_l+1^(w_l+2…^w_r))\mod p$.
分析
由扩展欧拉定理:
$$a^b\equiv \begincases a^b\%\phi(p)~~~~~~~~~~~gcd(a,p)=1\\ a^b~~~~~~~~~~~~~~~~~~gcd(a,p)\neq1,b<\phi(p)\\ a^b\%\phi(p)+\phi(p)~~~~gcd(a,p)\neq1,b\geq\phi(p) \endcases~~~~~~~(mod~p)$$
与BZOJ 3384中,次方是无限的,所以说指数一定大于 $\varphi(p)$,但是这道题中指数不一定大于 $\varphi(p)$,需要重写 Mod。
phi需要记忆话,不然会超时。
#include<bits/stdc++.h> using namespace std; typedef long long ll; const int maxn = 1e5 + 10; ll n, p, a[maxn]; unordered_map<int, int>phi; ll Mod(ll x, ll mod) return x < mod ? x : x % mod + mod; ll euler_phi(ll n) ll m = (ll)sqrt(n + 0.5); ll ans = n; for (ll i = 2; i <= m; i++) if (n % i == 0) ans = ans / i * (i - 1); while (n % i == 0) n /= i; //除尽 if (n > 1) ans = ans / n * (n - 1); //剩下的不为1,也是素数 return ans; ll get_phi(ll x) if(phi[x]) return phi[x]; return phi[x] = euler_phi(x); ll qpow(ll a, ll b, ll p) ll ret = 1; while(b) if(b&1) ret = Mod(ret * a, p); a = Mod(a * a ,p); b >>= 1; return ret; ll cal(ll l, ll r, ll p) //a^a^a..^a共b次 //printf("%lld %lld\n", t, p); //if(t == 1) return Mod(a, p); if(l == r) return Mod(a[l], p); if(p == 1) return Mod(a[l], p); ll phip = get_phi(p); return qpow(a[l], cal(l+1, r, phip), p); //第一类和第三类 int main() scanf("%I64d%I64d", &n, &p); for(int i = 1;i <= n;i++) scanf("%I64d", &a[i]); int q; scanf("%d", &q); while(q--) ll l, r; scanf("%I64d%I64d", &l, &r); printf("%I64d\n", cal(l, r, p) % p); //这个取模不能少 return 0;
参考链接:
1. https://blog.csdn.net/Charlie_jilei/article/details/79252689
2. https://blog.csdn.net/qq_35914587/article/details/79883547
以上是关于[CodeForces - 906D] Power Tower——扩展欧拉定理的主要内容,如果未能解决你的问题,请参考以下文章
CodeForces 906D Power Tower <<欧拉降幂
[CodeForces - 1225D]Power Products 数论 分解质因数
CodeForces 907F Power Tower(扩展欧拉定理)
codeforces Codeforces Round #597 (Div. 2) D. Shichikuji and Power Grid