高精度快速幂(算法描述)

Posted zwx7616

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了高精度快速幂(算法描述)相关的知识,希望对你有一定的参考价值。

板子题:

链接

题意

求2^p-1 的后500位和位数;

位数好求,最后一位-1,如果最后一位不是0 ,则无需往前借位,然而2^p不可能出现最后一位是0的情况;所以2^p-1和2^p位数相同。

对于求a^b问题,直接快速幂就好了

然鹅,这道题的数非常大,P(1000<P<31000001000<P<3100000)。最大的一个是P=3021377P=3021377,它有909526位。

普通快速幂

long long quick(int a,int b)

    ans=1;
    num=a;
    while(b)
    
        if(b&1)
            ans*=num;//只需要用数组进行模仿这两个乘法即可
        num*=num;//
        b>>=1;
    
    return ans;


模仿手算

#include<iostream>
#include<cmath>
#include<cstring>
using namespace std;
int n;
int num[505],ans[505],cnt[1005];

void operator_1()

    memset(cnt,0,sizeof(cnt));
    for(int i=1;i<=505;i++)
        for(int j=1;j<=505;j++)
        cnt[i+j-1]+=ans[i]*num[j];//运算的规律公式
    for(int i=1;i<505;i++)
        if(cnt[i]>=10)//进位检查并进位
    
        cnt[i+1]+=cnt[i]/10;
        cnt[i]%=10;
    
    memcpy(ans,cnt,sizeof(ans));//终于用上了这个复制公式


void operator_2()

    memset(cnt,0,sizeof(cnt));
    for(int i=1;i<=505;i++)
        for(int j=1;j<=505;j++)
       cnt[i+j-1]+=num[i]*num[j];
    for(int i=1;i<505;i++)
    if(cnt[i]>=10)
    
        cnt[i+1]+=cnt[i]/10;
        cnt[i]%=10;
    
    memcpy(num,cnt,sizeof(num));


void quick()

    while(n)
    
        if(n&1)
       operator_1();

       operator_2();
        n>>=1;
    


int main ()

    ans[1]=1;
    num[1]=2;
    cin>>n;
    cout<<(int)(log10(2)*n+1)<<endl;
    quick();
    ans[1]-=1;
    for(int i=500;i>=1;i--)
    
        if(i%50==0&&i!=500)
        cout<<endl;
        cout<<ans[i];
    
    return 0;

 

以上是关于高精度快速幂(算法描述)的主要内容,如果未能解决你的问题,请参考以下文章

随手练——麦森数(高精度快速幂)

快速幂(提速度)+快速乘(防爆精度)

算法初步:快速乘,快速幂,矩阵快速幂

整数快速乘法/快速幂+矩阵快速幂+Strassen算法 (转)

打工人必会的快速幂算法详解

快速幂详解