快速幂运算——原理以其应用(递归、迭代)

快速幂算法:

1,背景

给定三个整数a、b、m(a < 10^9, b < 10^6, 1< m < 10^9),求a^b%m

typedef long long LL;

LL pow(LL a, LL b, LL m){

    LL ans = 1;

    for (int i = 0; i < b; ++i) {

        ans = ans * a % m;

    }

    return  ans;

}

 

给定三个整数a、b、m(a < 10^9, b < 10^18,  1< m < 10^9),求a^b%m

这里用上面的做法显然是不行的,O(b)已经到了10^18

这里将使用快速幂算法

 

2,快速幂算法(递归)

a,如果b是奇数,那么有a^b = a* a^(b-1)

b,如果b是偶数,那么有a^b = a^(b/2)*a^(b/2)

这样,在log(b)级别次数的转换后,就可以把b转变为0,而任何正整数的0次方都是1

举个例子,如果计算2^10:

1)2^10———2^5, 2^10= 2^5*2^5

2)2^5———2^4,  2^5 = 2 * 2^4

3)2^4———2^2,  2^4 = 2^4 * 2*4

4)2^2———2^1,   2^2 = 2^1 *2^1

5)2^1———2^0,   2^1 = 2 * 2^0

6)2^0 = 1, 然后从下往上一次会退计算即可

这显然是递归的思想,于是可以得到快速幂的递归写法,时间复杂度为O(logb)

typedef long long LL;
LL binaryPow(LL a, LL b, LL m){
    if(b == 0) return 1;
    if(b % 2 == 1) //可以替换为 if(b&1)
        return  a * binaryPow(a, b - 1, m) % m;
    else{
        LL mu1 = binaryPow(a, b / 2, m);
/*不可直接返回binaryPow(a, b / 2, m)*binaryPow(a, b / 2, m)
因为会调用两次binaryPow函数,导致复杂度变为O(2^log(b)) = O(b)
*/
        return mu1 * mu1 % m;
    }
}

 

⚠️:

1)如果初始a有可能大于等于m,那么需要在进入函数前,就让a对m取模

2)如果m为1,可以直接在函数外部特判为0,不需要进入函数计算(因为任何正整数对1取模一定等于0)

 

3,快速幂算法(迭代)

对于a^b来说,如果把b写成二进制,那么b就可以写成若干次二次幂之和,

例如13的二进制1101,就可以写成13 = 2^3 + 2^2 +2^0 = 8 + 4 +1

所以a^13 = a^(8+4+1)=a^8 * a^4 * a^1

通过同样的方式,我们可以把任意的a^b表示为a^2k、。。。、a^8、a^4、a^2、a^1中若干项的乘积

步骤:

1)初始令ans为1,用来存放累计的结果

2)判断b的二进制末尾是否为1(即判断b&1 是否为1,也可以理解为判断b是否为奇数),如果是的话,令ans乘上a的值

3)令a平方,并将b右移一位(也可以理解为将b除以2)

4)只要b大于0,就返回2)

typedef long long LL;

LL binaryPow(LL a, LL b, LL m){

    LL ans = 1;

    while(b > 0){

        if(b & 1){      //如果b的二进制末尾为1

            ans = ans * a % m;//令ans累计a

        }

        a = a * a % m;      //令a开平方

        b >>= 1;           //将b的二进制右移一位

    }

    return ans;
}

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

繁星蓝雨

如果觉得文章不错,可以请喝咖啡

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值