麦森数
第一问:求2p-1的位数。事实上,我们关注2的幂次方的结尾:2,4,8,6,2…不断循环下去,且里面不包含0。因为也就是求2p的位数。怎么求?我们可以log10(2^p)+1来表示,若根据对数函数的性质,我们可以变形为:p*log10(2)+1。第一问就这么解决了。
第二问:设计两个知识点,快速幂和高精度。(高精度,快速幂)这里不做过多阐述。
CODE
#include<bits/stdc++.h>
using namespace std;
#define MAXN 1200
int p;
int res[MAXN];
int pwNUM[MAXN];
inline void read(int &be_readNUM)
{
int s=0,w=1;char c=getchar();
while (c<'0' || c>'9') c=getchar();
while (c<='9' && c>='0') {s=s*10+c-'0'; c=getchar();}
be_readNUM=s*w;return;
}
void Plus()
{
int temp[MAXN]={};
for (int i=1;i<=500;++i)
for (int j=1;j<=500;++j)
temp[i+j-1]+=res[i]*pwNUM[j];
for (int i=1;i<=500;++i)
{
temp[i+1]+=temp[i]/10;
temp[i]%=10;
}
for (int i=1;i<=500;++i) res[i]=temp[i];
return;
}
void Power()
{
int temp[MAXN]={};
for (int i=1;i<=500;++i)
for (int j=1;j<=500;++j)
temp[i+j-1]+=pwNUM[i]*pwNUM[j];
for (int i=1;i<=500;++i)
{
temp[i+1]+=temp[i]/10;
temp[i]%=10;
}
for (int i=1;i<=500;++i) pwNUM[i]=temp[i];
return;
}
int main()
{
read(p);
printf("%d\n",int(p*log10(2)+1));
res[1]=1;pwNUM[1]=2;
while (p>0)
{
if (p%2==1) Plus();
p/=2;
Power();
}
res[1]--;
for (int i=1;i<=500;++i)
if (i%50==0) printf("%d\n",res[501-i]);
else printf("%d",res[501-i]);
return 0;
}