题干:
给你A,B,C,让你快速求出 A^B mod C. (1<=A,C<=1000000000,1<=B<=10^1000000).
思路:
因为B也就是幂数特别大,所以直接快速幂一定会超时,这时我们需要使B在模C的情况下减小,使用欧拉降幂。
A
B
A^B
AB mod C= A^(B mod phi(c ) ) mod C …(B<phi(c ))
A
B
A^B
AB mod C= A^(B mod phi(c )+phi(C )) mod C …(B>=phi(c ))
phi(c )为c的欧拉函数
贴个欧拉降幂的讲解https://blog.csdn.net/qq_37632935/article/details/81264965
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <vector>
#include <cmath>
#include <map>
#include <algorithm>
using namespace std;
const long long mx=1e7+10;
long long a,c;
char b[mx];
long long olc(long long n)
{
long long ans=n;
for(int i=2;i*i<=n;i++){
if(n%i==0)
{
ans-=ans/i;
while(n%i==0)
n/=i;
}
}
if(n>1) ans-=ans/n;
return ans;
}
long long qc(long long n,long long m)
{
long long now=1;
while(m)
{
if(m&1)
{
now=(now*n)%c;
}
n=(n*n)%c;
m>>=1;
}
return now;
}
int main()
{
while(scanf("%lld%s%lld",&a,b,&c)!=EOF)
{
long long l=strlen(b),now=0,oc=olc(c),i;
for(i=0;i<l;i++){
now=now*10+b[i]-'0';
if(now>oc) break;
}
if(i==l)
printf("%lld\n",qc(a,now));
else
{
now=0;
for(i=0;i<l;i++){
now=(now*10+b[i]-'0')%oc;
}
printf("%lld\n",qc(a,now+oc));
}
}
return 0;
}