【L​eetCode随手玩】 Divide Two Integers - 解题方式

29. Divide Two Integers (两数相除)

大家好,我是一个喜欢研究算法、机械学习和生物计算的小青年,我的CSDN博客是:一骑代码走天涯
如果您喜欢我的笔记,那么请点一下关注、点赞和收藏。如果內容有錯或者有改进的空间,也可以在评论让我知道。😄

题目描述

这道题目给了两个数字,分別是被除数和除数,然后你要找到它们的商数 (余数不用理会)。这道题的难点在于不能直接用整除法或乘法找答案,严格上连这两种符号 (包括mod) 都不能使用。而且,数字限制为 32-bit 整数,所以在处理正负数时必须格外注意。

在以下的解题中,我会用两种解法。第一种是对题目不太严谨的,虽然没直接用除法找答案,但因為是用二分搜索 (binary search),所以还是用了一次来找中间数。第二种是用了bit manipulation,是参考了其他资料才明白的。相关资料我会放在参考资料上,有兴趣的可以看看。

题目原文(英语)

按此进入题目链结

Given two integers dividend and divisor, divide two integers without using multiplication, division and mod operator.
Return the quotient after dividing dividend by divisor.
The integer division should truncate toward zero, which means losing its fractional part. For example, truncate(8.345) = 8 and truncate(-2.7335) = -2.

Example 1:
Input: dividend = 10, divisor = 3
Output: 3
Explanation: 10/3 = truncate(3.33333…) = 3.

Example 2:
Input: dividend = 7, divisor = -3
Output: -2
Explanation: 7/-3 = truncate(-2.33333…) = -2.

Note:

  • Both dividend and divisor will be 32-bit signed integers.
  • The divisor will never be 0.
  • Assume we are dealing with an environment which could only store integers within the 32-bit signed integer range: [−231, 231 − 1]. For the purpose of this problem, assume that your function returns 231 − 1 when the division result overflows.

解题方式 (一)

第一个方法理解比较简单。首先,我们先处理个別情況,例如 除数为 1或-1被除数为0整除后超过32-bit 的介限。这些情況我用 if-clause 来先搞定。然后,用neg先存着答案是否负数 (-1为负,1为正),再用二分搜索找出答案 (返回前乘以neg)。

class Solution:
    def divide(self, dividend: int, divisor: int) -> int:
        if dividend == (-2**31) and divisor == -1:
            return ((2**31) - 1)
        if dividend == 0 or abs(divisor) > abs(dividend):
            return 0
        if divisor == 1:
            return dividend
        if divisor == -1:
            return dividend * -1
        if dividend == divisor:
            return 1
        
        neg = 1
        if dividend < 0:
            neg *= -1
            dividend = abs(dividend)
        if divisor < 0:
            neg *= -1
            divisor = abs(divisor)
        left = 1
        right = dividend
        while left < right:
            mid = (left + right) // 2
            tmp = dividend - divisor * mid 
            if 0 <= tmp < divisor:
                print('true')
                return mid * neg
            elif tmp < 0:
                right = mid - 1
            elif tmp > divisor:
                left = mid + 1
        print('left')
        return left * neg

解题方式 (二)

第二个方法就是用 bit manipulation。一开始也是一样,先处理好不同的个別情況;之后就可以採取bit operation。主要是我在这一塊儿也需要多加努力,所以我就不多赘述了。

class Solution:
    def divide(self, dividend: int, divisor: int) -> int:
        if dividend == (-2**31) and divisor == -1:
            return ((2**31) - 1)
        if dividend == 0 or abs(divisor) > abs(dividend):
            return 0
        if divisor == 1:
            return dividend
        if divisor == -1:
            return dividend * -1
        if dividend == divisor:
            return 1
        
        sign = (-1 if((dividend < 0) ^ (divisor < 0)) else 1); 
        dividend = abs(dividend)
        divisor = abs(divisor)
        quotient = 0
        temp = 0
        for i in range(31, -1, -1): 
            if (temp + (divisor << i) <= dividend): 
                temp += divisor << i
                quotient |= 1 << i
        return sign * quotient;

参考资料

https://www.geeksforgeeks.org/divide-two-integers-without-using-multiplication-division-mod-operator/

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值