【LeetCode-剑指offer】--1.两数相除

文章介绍了如何通过减法和乘法的结合计算两数相除,避免整数溢出问题,包括转换数的正负、判断溢出情况和使用异或操作确定结果的正负。Solution类中详细展示了这个过程。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1.两数相除

image-20231228114055707

方法:使用减法实现除法

用“被减数”能减去几次“减数”来衡量最后的结果,这时候我们想到求x的幂次的快速解法,将x成倍成倍的求幂,这里将减数成倍成倍的增大,次数对应也是成倍成倍的增大,例如:取a=23,b=2,b的变化如下:2->4->8->16,次数count的变化如下1->2->4->8,最后a-b=23-16=7,对7再执行一次上述过程,b:2->4,count:1->2,a-b=3, 然后对3再执行一次,b:2,count:1,a-b=1,1已经小于原b=2,可以结束了,最后计数一下每轮的count是多少8+2+1=11,就是我们要的答案

为方便运算,我们需要将a,b都转为同正or同负,由于INT_MIN转正就越界了,我们只好都转负,这也是都转负的原因;

有一种特殊情况 INT_MIN/(-1)就overflow了 所以直接特殊处理

class Solution {
    public int divide(int a, int b) {
        //产生溢出
        if(a == Integer.MIN_VALUE && b == -1){
            return Integer.MAX_VALUE;
        }
        //异或操作,判断正负号
        int sign = (a > 0) ^ (b > 0) ? -1:1;
        if(a > 0) a = -a;
        if(b > 0) b = -b;
        int res = 0;
        while(a <= b){  //a的绝对值大
            int base = b;
            int k = 1;
            //由于a <= base + base可能溢出,改成a - base <= base
            while( a - base <= base){
                base += base;  //可以减的次数翻倍
                k += k;  //减数也翻倍
            }
            a -= base;
            res += k;
        }
        return sign * res;
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值