1. 题目
Divide two integers without using multiplication, division and mod operator.
If it is overflow, return MAX_INT.
2. 思路
这题的异常考虑点的坑很多。各种溢出。
先转正,再用二进制移位比较计算。
基本思路就是二进制,用移位和加减法来完成。
按二进制的最高位开始匹配,依次得到二进制下的所有非0位。
注意:正负数的处理。
注意:-max转为正数时会溢出,比如 -max/-1 = max + 1 溢出。
注意:由于做了负数转正,-max不能直接转换为正数。这里会导致溢出得到一个0值,于是就容易死循环了。
3. 代码
耗时:9ms
class Solution {
public:
int divide(int dividend, int divisor) {
if (dividend == -2147483648 && divisor == -1) return 2147483647;
if (dividend == -2147483648 && divisor == 1) return -2147483648;
// @warning: 这里是一个坑,如果不扩展到long long上去,当某一个数为-2147483648时,取负会溢出,于是整体就错误最终导致除0的TLM
long long de = dividend > 0 ? dividend : -1LL * dividend;
long long di = divisor > 0 ? divisor : -1LL * divisor;
long long flag = 1;
if (dividend > 0 && divisor < 0 || dividend < 0 && divisor > 0) flag = -1;
if (de < di) return 0;
//if (di == 0) return 2147483647;
long long res = 0;
while (de >= di) {
long long k = 0;
long long v = di;
while (de >= v) {
v <<= 1;
k++;
}
k--;
v >>= 1;
res += (1 << k);
de -= v;
if (de < di) {
return flag * res;
}
}
return res * flag;
}
};