法一:运用位运算简化计算
以 \(3^{22}\) 为例,它的底数为 \(3\),指数为 \(22\)。指数的二进制形式为 10110
。通过二进制与十进制的转换,我们可以把 \(22\) 分解为 \(22 = 2^4 * 2^2 * 2^1\)。因此,\(3^{22} = 3^{2^4} * 3^{2^2} * 3^{2^1}\)。我们有以下几点发现:
- 1、\(2^4\), \(2^2\) 和 \(2^1\) 与二进制形式中 \(1\) 的出现位置有关,那么,这也导致 \(3^{2^4}\), \(3^{2^2}\) 和 \(3^{2^1}\) 有这样的关系。
- 2、我们知道,在二进制中,相邻的两位,从“右边到左边”要
× 2
。比如,\(2^2 = 2^1 \times 2\); 由于中间隔了一个 \(0\),所以要乘两个2
,\(2^3 = 2^2 \times 2~\Rightarrow~2^4 = 2^3 \times 2\)。反应到 \(3^{22}\) 上,就变成了平方
关系。比如,\(3^{2^2} = 3^{2^1} \times 3^{2^1}\); 由于中间隔了一个 \(0\),所以要平方
两次,\(3^{2^3} = 3^{2^2} \times 3^{2^2}~\Rightarrow~3^{2^4} = 3^{2^3} \times 3^{2^3}\)。
ll quick_pow(ll x, ll n, ll mod)
{
ll ans = 1;
while (n > 0)
{
if (n & 1)
ans = ans * x % mod;
x = x * x % mod;
n >>= 1;
}
return ans;
}
法二:运用递归的思想
对于 \(x^n\),有
\[\begin{split} x^n = \begin{cases} {(x^2)}^{\lfloor n / 2\rfloor}&,n为偶数 \\ {(x^2)}^{\lfloor n / 2\rfloor} \ast x&,~n为奇数 \end{cases} \end{split} \]令 \(x^n =\) quick_pow(x, n)
,则递归方程:
ll quick_pow(ll x, ll n, ll mod)
{
if (n == 0) return 1;
ll ans = quick_pow1(x * x % mod, n / 2, mod);
if (n & 1) ans = ans * x % mod;
return ans;
}
完
标签:22,ll,times,ans,quick,快速,mod From: https://www.cnblogs.com/hoyd/p/18016249