描述
形如2^P-1的素数称为麦森数,这时P一定也是个素数。但反过来不一定,即如果P是个素数,2^P-1不一定也是素数。到1998年底,人们已找到了37个麦森数。最大的一个是P=3021377,它有909526位。麦森数有许多重要应用,它与完全数密切相关。
任务:从文件中输入P(1000<P<3100000),计算2^P-1的位数和最后500位数字(用十进制高精度数表示)
输入
文件中只包含一个整数P(1000<P<3100000)
输出
第一行:十进制高精度数2^P-1的位数。
第2-11行:十进制高精度数2^P-1的最后500位数字。(一行输出,不足500位时高位补0)
不必验证2^P-1与P是否为素数。
样例输入
1279
样例输出
386
00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000010407932194664399081925240327364085538615262247266704805319112350403608059673360298012239441732324184842421613954281007791383566248323464908139906605677320762924129509389220345773183349661583550472959420547689811211693677147548478866962501384438260291732348885311160828538416585028255604666224831890918801847068222203140521026698435488732958028878050869736186900714720710555703168729087
题意
先输出十进制高精度数2^P-1的位数再输出最后500位
题解
这里求位数我推了好久,其实求位数有个公式:log10(a)*p+1,表示a^p的位数
这里-1不影响总位数,因为2的倍数末尾只可能是2,4,6,8
算500位采用快速幂的思想:2^5==(2^2)^2*2 其中2^2==(2^1)^2
然后模拟一下乘2和平方即可,注意算平方的时候不能越界
代码
1 #include<stdio.h> 2 #include<math.h> 3 #include<string.h> 4 int a[505]; 5 void digui(int x){//快速幂思想 6 if(x/2!=1) 7 digui(x/2); 8 pifang(); 9 if(x%2==1) 10 cheng(); 11 } 12 void cheng(){//乘2 13 int i; 14 for(i=500;i>=1;i--) 15 a[i]*=2; 16 for(i=500;i>=1;i--){ 17 if(a[i]>=10){ 18 a[i-1]+=a[i]/10; 19 a[i]%=10; 20 } 21 } 22 } 23 void pifang(){//平方 24 int i,j,p[505]; 25 memset(p,0,sizeof(p)); 26 for(i=500;i>=1;i--) 27 for(j=500;j>=1;j--) 28 if(i+j-500>=1)//注意这里不能越界 29 p[i+j-500]+=a[i]*a[j]; 30 for(i=500;i>=1;i--){ 31 if(p[i]>=10){ 32 p[i-1]+=p[i]/10; 33 p[i]%=10; 34 } 35 } 36 for(i=1;i<=500;i++) 37 a[i]=p[i]; 38 } 39 40 int main(){ 41 int i,p; 42 memset(a,0,sizeof(a)); 43 scanf("%d",&p); 44 printf("%d ",(int)(p*log10(2))+1);//直接套公式 45 a[500]=2; 46 digui(p); 47 a[500]--; 48 for(i=1;i<=500;i++) 49 printf("%d",a[i]); 50 puts(""); 51 return 0; 52 }