从二进制角度理解快速乘与快速幂

本文介绍了从二进制角度理解快速乘法和快速幂的方法,讲解了如何利用二进制拆分进行高效计算。通过十进制与二进制转换,结合位操作,详细阐述了快速乘法的模板,并以3*9为例进行演示。同时,对比快速乘法,快速幂将加法转换为乘法,进一步优化了计算过程。

前提知识:

十进制与二进制相互转换
n&1 (与操作): 判断 n 二进制最右一位是否为 1如为1则返回真
n>>1 (移位操作): n 右移一位(可理解为删除最后一位,n除以2)


快速乘法模板:

无论是快速乘法a∗ba*bab还是快速幂 aba^{b}ab ,对其进行二进制拆分,把b拆成二进制形式。
a∗b=a∗(a*b=a*(ab=a(ck-1∗2k−1+*2^{k-1}+2k1+ck-2∗2k−2+*2^{k-2}+2k2+ck-3∗2k−3+*2^{k-3}+2k3++++c0∗20*2^{0}20)其中c就是二进制位是否为1
例如:3*9
9转换成二进制为1001,那么原式= 3∗9=3∗(3*9=3*(39=3( 1∗23+*2^{3}+23+ 0∗22+*2^{2}+22+ 0∗21+*2^{1}+21++++ 1∗20*2^{0}20)
代码如下:

@Override
	static long mul(long a, long k) {
		//返回的结果
        long ans = 0;
        
        while (k > 0) {
        	//判断二进制的那一位是否为1,若为1则+不为1则跳过
            if ((k & 1) == 1) ans += a;
            //右移操作
            k >>= 1;
            //a自加相当于乘以2
            a += a;
        }
        return ans;
    }

快速幂:

无论是快速乘法a∗ba*bab还是快速幂 aba^{b}ab ,对其进行二进制拆分,把b拆成二进制形式。
ab=a^{b}=ab= a^(ck-1∗2k−1+*2^{k-1}+2k1+ck-2∗2k−2+*2^{k-2}+2k2+ck-3∗2k−3+*2^{k-3}+2k3++++c0∗20*2^{0}20)其中c就是二进制位是否为1,于快速乘在代码中有所区别的地方在于将加法变成了乘法。

@Override
static double myPow(double x, int n) {
                if(x == 0.0f) return 0.0d;
        long b = n;
        double ans = 1.0;
        //判断n是否小于0,小于0转换成分数
        if (b < 0){
            x = 1/x;
            b = -b;
        }
        while(b >0){
            if((b&1)==1) ans*=x;
            b=b>>1;
            x*=x;
        }
        return ans;
    }

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值