快速幂取模、大整数快速幂以及优化
快速幂取模:
LL pow(LL a, LL n, LL p) //快速幂 a^n % p { LL ans = 1; while(n) { if(n & 1) ans = ans * a % p; //若不取模就去掉p a = a * a % p; n >>= 1; } return ans; }
大数快速幂(未优化):
typedef unsigned long long LL; string str; int input[10000005]; int output[10000005]; int len; int sum=1,d=0,k=0; void to_bin(string str) //将大整数转换为二进制,转换后为逆序 { len=str.size(); for(int i=0;i<len;i++) input[i]=str[i]-0; memset(output,0,sizeof(output)); sum=1,d=0,k=0; while(sum) { sum = 0; for(int i=0;i<len;i++){ d = input[i] / 2; sum += d; if(i == (len - 1)){ output[k++] = input[i] % 2; } else input[i+1] += (input[i]%2)*10; input[i] = d; } } } LL pow(LL a, int n[], LL p) //快速幂 a^n % p { LL ans = 1; int i=0; while(i<k) { if(n[i] == 1) ans = ans * a % p; a = a * a % p; i++; } return ans; } int main() { LL a,b,c; while(cin>>a>>str>>c) { to_bin(str); cout<<pow(a,output,c)<<endl; } }
大整数快速幂(优化版):O(nlog(n))
#include <bits/stdc++.h> using namespace std; const int mod=1e9+7; long long quick_mod(long long a,long long b) { long long ans=1; while(b){ if(b&1){ ans=(ans*a)%mod; b--; } b/=2; a=a*a%mod; } return ans; }//内部也用快速幂 long long quickmod(long long a,char *b,int len) { long long ans=1; while(len>0){ if(b[len-1]!=0){ int s=b[len-1]-0; ans=ans*quick_mod(a,s)%mod; } a=quick_mod(a,10)%mod; len--; } return ans; } int main(){ char s[100050]; int a; while(~scanf("%d",&a)) //求a^s%mod { scanf("%s",s); int len=strlen(s); printf("%I64d ",quickmod(a,s,len)); } return 0; }