29. 两数相除
难度中等565收藏分享切换为英文接收动态反馈
给定两个整数,被除数 dividend
和除数 divisor
。将两数相除,要求不使用乘法、除法和 mod 运算符。
返回被除数 dividend
除以除数 divisor
得到的商。
整数除法的结果应当截去(truncate
)其小数部分,例如:truncate(8.345) = 8
以及 truncate(-2.7335) = -2
示例 1:
输入: dividend = 10, divisor = 3
输出: 3
解释: 10/3 = truncate(3.33333..) = truncate(3) = 3
示例 2:
输入: dividend = 7, divisor = -3
输出: -2
解释: 7/-3 = truncate(-2.33333..) = -2
提示:
- 被除数和除数均为 32 位有符号整数。
- 除数不为 0。
- 假设我们的环境只能存储 32 位有符号整数,其数值范围是 [−231, 231 − 1]。本题中,如果除法结果溢出,则返回 231 − 1。
- Divide Two Integers
Medium
17756872Add to ListShare
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
.
Note: Assume we are dealing with an environment that could only store integers within the 32-bit signed integer range: [−231, 231 − 1]
. For this problem, assume that your function returns 231 − 1
when the division result overflows.
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.
Example 3:
Input: dividend = 0, divisor = 1
Output: 0
Example 4:
Input: dividend = 1, divisor = 1
Output: 1
Constraints:
-231 <= dividend, divisor <= 231 - 1
divisor != 0
先实现
- 加法
public static int add(int a, int b) {
int sum = a;
while (b != 0) {
sum = a ^ b;
b = (a & b) << 1;
a = sum;
}
return sum;
}
- 减法
a-b = a+(-b)
public static int negNum(int n) {
return add(~n, 1);
}
public static int minus(int a, int b) {
return add(a, negNum(b));
}
- 乘法
public static int multi(int a, int b) {
int res = 0;
while (b != 0) {
if ((b & 1) != 0) {
res = add(res, a);
}
a <<= 1;
b >>>= 1;
}
return res;
}
- 除法
public static boolean isNeg(int n) {
return n < 0;
}
public static int div(int a, int b) {
int x = isNeg(a) ? negNum(a) : a;
int y = isNeg(b) ? negNum(b) : b;
int res = 0;
for (int i = 31; i > negNum(1); i = minus(i, 1)) {
if ((x >> i) >= y) {
res |= (1 << i);
x = minus(x, y << i);
}
}
return isNeg(a) ^ isNeg(b) ? negNum(res) : res;
}
public static int divide(int dividend, int divisor) {
if (divisor == Integer.MIN_VALUE) {
return dividend == Integer.MIN_VALUE ? 1 : 0;
}
// 除数不是系统最小
if (dividend == Integer.MIN_VALUE) {
if (divisor == negNum(1)) {
return Integer.MAX_VALUE;
}
int res = div(add(dividend, 1), divisor);
return add(res, div(minus(dividend, multi(res, divisor)), divisor));
}
// dividend不是系统最小,divisor也不是系统最小
return div(dividend, divisor);
}
完整代码
class Solution {
public static int add(int a, int b) {
int sum = a;
while (b != 0) {
sum = a ^ b;
b = (a & b) << 1;
a = sum;
}
return sum;
}
public static int negNum(int n) {
return add(~n, 1);
}
public static int minus(int a, int b) {
return add(a, negNum(b));
}
public static int multi(int a, int b) {
int res = 0;
while (b != 0) {
if ((b & 1) != 0) {
res = add(res, a);
}
a <<= 1;
b >>>= 1;
}
return res;
}
public static boolean isNeg(int n) {
return n < 0;
}
public static int div(int a, int b) {
int x = isNeg(a) ? negNum(a) : a;
int y = isNeg(b) ? negNum(b) : b;
int res = 0;
for (int i = 31; i > negNum(1); i = minus(i, 1)) {
if ((x >> i) >= y) {
res |= (1 << i);
x = minus(x, y << i);
}
}
return isNeg(a) ^ isNeg(b) ? negNum(res) : res;
}
public static int divide(int dividend, int divisor) {
if (divisor == Integer.MIN_VALUE) {
return dividend == Integer.MIN_VALUE ? 1 : 0;
}
// 除数不是系统最小
if (dividend == Integer.MIN_VALUE) {
if (divisor == negNum(1)) {
return Integer.MAX_VALUE;
}
int res = div(add(dividend, 1), divisor);
return add(res, div(minus(dividend, multi(res, divisor)), divisor));
}
// dividend不是系统最小,divisor也不是系统最小
return div(dividend, divisor);
}
// div(a,b) a和b都不能是系统最小
public static String printNumBinary(int num) {
StringBuilder builder = new StringBuilder();
for (int i = 31; i >= 0; i--) {
builder.append(((num >> i) & 1) == 0 ? '0' : '1');
}
return builder.toString();
}
}