-
Notifications
You must be signed in to change notification settings - Fork 0
/
int.go
140 lines (126 loc) · 2.44 KB
/
int.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
package algorithm
import "math"
/*
29. 两数相除
思路:加法(超时)
*/
func divide(dividend int, divisor int) int {
if divisor == 0 || dividend == 0 {
return 0
}
isResultN := false
if (dividend > 0 && divisor < 0) || (dividend < 0 && divisor > 0) {
isResultN = true
}
dividend = int(math.Abs(float64(dividend)))
divisor = int(math.Abs(float64(divisor)))
sum := 0
divide := 0
for sum + divisor <= dividend {
sum = sum + divisor
divide ++
}
if isResultN {
divide = -divide
}
if divide < math.MinInt32 {
return math.MinInt32
}
if divide > math.MaxInt32 {
return math.MaxInt32
}
return divide
}
// 快速乘
// x 和 y 是负数,z 是正数
// 判断 z * y >= x 是否成立
func quickAdd(y, z, x int) bool {
for result, add := 0, y; z > 0; z >>= 1 { // 不能使用除法
if z&1 > 0 {
// 需要保证 result + add >= x
if result < x-add {
return false
}
result += add
}
if z != 1 {
// 需要保证 add + add >= x
if add < x-add {
return false
}
add += add
}
}
return true
}
func divide2(dividend, divisor int) int {
if dividend == math.MinInt32 { // 考虑被除数为最小值的情况
if divisor == 1 {
return math.MinInt32
}
if divisor == -1 {
return math.MaxInt32
}
}
if divisor == math.MinInt32 { // 考虑除数为最小值的情况
if dividend == math.MinInt32 {
return 1
}
return 0
}
if dividend == 0 { // 考虑被除数为 0 的情况
return 0
}
// 一般情况,使用二分查找
// 将所有的正数取相反数,这样就只需要考虑一种情况
rev := false
if dividend > 0 {
dividend = -dividend
rev = !rev
}
if divisor > 0 {
divisor = -divisor
rev = !rev
}
ans := 0
left, right := 1, math.MaxInt32
for left <= right {
mid := left + (right-left)>>1 // 注意溢出,并且不能使用除法
if quickAdd(divisor, mid, dividend) {
ans = mid
if mid == math.MaxInt32 { // 注意溢出
break
}
left = mid + 1
} else {
right = mid - 1
}
}
if rev {
return -ans
}
return ans
}
/*
50. Pow(x, n)
https://leetcode-cn.com/problems/powx-n/
思路:递归
1、当n为偶数:x = x^(n/2) * x^(n/2)
2、当n为奇数:x = x^(n/2) * x^(n/2) * x
*/
func myPow(x float64, n int) float64 {
if n >= 0 {
return quickMul(x, n)
}
return 1.0 / quickMul(x, -n)
}
func quickMul(x float64, n int) float64 {
if n == 0 {
return 1
}
y := quickMul(x, n/2)
if n%2 == 0 {
return y * y
}
return y * y * x
}