【模板】快速幂
题目描述
给你三个整数 a , b , p a,b,p a,b,p,求 a b m o d p a^b \bmod p abmodp。
输入格式
输入只有一行三个整数,分别代表 a , b , p a,b,p a,b,p。
输出格式
输出一行一个字符串 a^b mod p=s
,其中
a
,
b
,
p
a,b,p
a,b,p 分别为题目给定的值,
s
s
s 为运算结果。
样例 #1
样例输入 #1
2 10 9
样例输出 #1
2^10 mod 9=7
提示
样例解释
2 10 = 1024 2^{10} = 1024 210=1024, 1024 m o d 9 = 7 1024 \bmod 9 = 7 1024mod9=7。
数据规模与约定
对于 100 % 100\% 100% 的数据,保证 0 ≤ a , b < 2 31 0\le a,b < 2^{31} 0≤a,b<231, a + b > 0 a+b>0 a+b>0, 2 ≤ p < 2 31 2 \leq p \lt 2^{31} 2≤p<231。
思路
快速幂算法的主要思想是将指数 b b b进行分解,然后利用乘法的分配性质和取模的性质,将原问题转化为多个子问题的求解,从而大大提高了计算效率。
如果 b b b是偶数,那么 a b m o d p = ( a b / 2 m o d p ) 2 m o d p a^b \mod p = (a^{b/2} \mod p)^2 \mod p abmodp=(ab/2modp)2modp;如果 b b b是奇数,那么 a b m o d p = ( a b − 1 m o d p ) × a m o d p a^b \mod p = (a^{b-1} \mod p) \times a \mod p abmodp=(ab−1modp)×amodp。这样,我们就可以将原问题不断分解为规模更小的子问题,直到 b b b等于0,此时 a 0 a^0 a0等于1。
在计算大数的乘方时,结果往往会非常大,导致溢出。为了避免这种情况,在每一步计算中都取模。
AC代码
#include <iostream>
#define ll long long
#define AUTHOR "HEX9CF"
using namespace std;
ll qpow(int a, int b, int p) {
if (!b) {
return 1;
}
if (b % 2 == 1) {
return (qpow(a, b - 1, p) * a) % p;
} else {
ll tmp = qpow(a, b >> 1, p) % p;
return (tmp * tmp) % p;
}
return 0;
}
int main() {
int a, b, p;
cin >> a >> b >> p;
ll ans = qpow(a, b, p);
printf("%d^%d mod %d=%lld", a, b, p, ans);
return 0;
}