乘方
[Description]
第一个考验还没弄完,第二个考验又来了……存心不让我去啊!!!计算
2x mod y
由于时间紧迫,而且 Jiangzh 又是蒟蒻,所以就只能求助你们了
[Input]
一行两个整数 x 和 y,用空格隔开
[Output]
一行一个整数,最后的答案
[Sample 1]
math.in |
math.out |
|
|
3 3 |
2 |
|
|
样例解释:23=8 ,8%3=2 |
|
[Hit]
对于 10%的数据:x<=26 – 1 对于 20%的数据:x<=217 – 1 对于 40%的数据:x<=264 – 1 对于 70%的数据:x<=2333 – 1
对于 100%的数据:x<=2233333 – 1 ,y 为 [3,1000] 的质数
70分[高精度+快速幂]
#include<cstdio> #include<cstring> typedef long long LL; struct BigInt{ int c[20000],len; BigInt() { memset(c,0,sizeof(c)); len=1; } void Read() { char s[2000000]; scanf("%s",s); int l=strlen(s); int k=1; len=1; memset(c,0,sizeof(c)); for(int i=l-1;i>=0;i--) { c[len]+=(s[i]-'0')*k; if((k*=10)==100000) k=1,len++; } } void Zero() { while(len>1 && c[len]==0) len--; } bool operator == (int a) { return len==1 && c[len]==a; } BigInt operator / (int a) { for(int i=len;i>=1;i--) { if(i!=1) c[i-1]+=(c[i]%a)*100000; c[i]/=a; } Zero(); return *this; } int operator & (int a) { return c[1]&a; } }y; int x=2,mod; int mul(int x,BigInt y,int mod) { int ans=1; while(1) { if(y&1) ans=((LL)ans*x%mod)%mod; x=((LL)x%mod*x%mod)%mod; y=y/2; if(y==1) break; } ans=((LL)ans*x%mod)%mod; return ans%mod; } int main() { freopen("math.in","r",stdin); freopen("math.out","w",stdout); y.Read(); scanf("%d",&mod); printf("%d\n",mul(x,y,mod)); return 0; }
费马小定理
推得
2a%mod = 2a%(mod-1)%mod
算法实现↓
#include<cstdio> #include<cstring> typedef long long LL; int x=2,y,mod; char s[2000000]; int mul(int x,int y,int mod) { if(y==0) return 1; if(y==1) return x; int ans=1; while(1) { if(y&1) ans=((LL)ans*x%mod)%mod; x=((LL)x%mod*x%mod)%mod; y=y/2; if(y==1) break; } ans=((LL)ans*x%mod)%mod; return ans%mod; } int main() { freopen("math.in","r",stdin); freopen("math.out","w",stdout); scanf("%s",s); int slen=strlen(s); scanf("%d",&mod); y=0;int last=0; for(int i=0;i<slen;i++) { y=(last*10+(s[i]-'0'))%(mod-1); last=y%(mod-1); } printf("%d\n",mul(x,y,mod)); return 0; }