快速幂算法详解

注明:本文中的xy表示x的y次方

当你要求n的m次方模k的值时,你应该用什么算法来做呢?

一、O(m)朴素算法

最简单的方法,便是朴素的模拟,这里就不多加介绍了,代码见下:

#include<bits/stdc++.h>
#define LL long long 
using namespace std;
LL n,m,k;
int main()
{	
    scanf("%lld%lld%lld",&n,&m,&k);	
    LL res=1;	
    for(int i=1;i<=m;i++) (res*=n)%=k;	
    printf("%lld",res);	
    return 0;
}

二、快速幂算法

可是,O(m)的朴素算法毕竟还是太慢了,所以,我们需要一个效率更高的算法——快速幂。

对于x的y次方,我们可以进行分类讨论:

当y为偶数时,xy=xy/2*xy/2;

当y为奇数时,xy=xy/2*xy/2*x("/"表示整除)

于是,我们很容易就能想出一个O(log2m)的算法,也就是所谓的快速幂算法:

①建立一个long long类型的变量res来存储答案

扫描二维码关注公众号,回复: 161972 查看本文章

②判断m的奇偶性,若为奇数,则将res乘上n,并向k取模

③n平方,m整除2

④若m不为0,则返回②

具体代码如下:

#include<bits/stdc++.h>
#define max(x,y) (x>y?x:y)
#define min(x,y) (x<y?x:y)
#define LL long long
using namespace std;
LL n,m,k;LL Counting(LL x,LL y,LL MOD)//快速幂函数 
{	
    LL res=1;//存储结果 	
    while(y>0) {if(y&1) (res*=x)%=MOD;(x*=x)%=MOD,y>>=1;}//y&1相当于y%2,y>>=1相当于y/=2,用位运算加快速度 	
    return res;
}
int main()
{
    scanf("%lld%lld%lld",&n,&m,&k);
    printf("%lld",Counting(n,m,k));
    return 0;
}



注:如果您通过此文学会了快速幂算法,请您点个赞再离开。当然,也欢迎在讨论区指出此文的不足处,作者会及时对此文加以修正
版权声明:转载请注明地址


猜你喜欢

转载自blog.csdn.net/chenxiaoran666/article/details/79768458