數學相關
阿新 • • 發佈:2018-12-11
目錄
166分數到小數
給定兩個整數,分別表示分數的分子 numerator 和分母 denominator,以字串形式返回小數。如果小數部分為迴圈小數,則將迴圈的部分括在括號內。
輸入: numerator = 2, denominator = 3
輸出: "0.(6)"
思路:
- 分母、分子為0的情況
- 新建StringBuilder
- 結果是否為負數,是則加上負號
- 分子分母取絕對值
- 處理整數部分,並判斷是否可以整除,是的話返回結果。注意轉為long,且用
long rem = (num % den) * ,10;
- 不能整除,那麼加上小數點,新建map,用來儲存餘數及當前結果的長度
- 只要餘數不為0,那麼進入迴圈。
- 檢查map中,當前餘數是否已經出現過,如果是,取值,substring處理迴圈部分
- 更新map、res和rem
- 返回res.toString()
// 分母、分子為0的情況 if (denominator == 0) return ""; if (numerator == 0) return "0"; StringBuilder res = new StringBuilder(); // 結果是否為負數 if ((numerator < 0) ^ (denominator < 0)) res.append("-"); // 取絕對值,方便處理 long num = numerator, den = denominator; num = Math.abs(num); den = Math.abs(den); // 整數部分 res.append(num / den); long rem = (num % den) * 10; if (rem == 0) return res.toString(); // 負數部分 res.append("."); HashMap<Long, Integer> map = new HashMap<Long, Integer>(); while (rem != 0) { if (map.containsKey(rem)) { Integer loc = map.get(rem); String p1 = res.substring(0, loc); String p2 = res.substring(loc); res = new StringBuilder(p1 + "(" + p2 + ")"); return res.toString(); } map.put(rem, res.length()); res.append(rem / den); rem = (rem % den) * 10; } return res.toString();
169/229求眾數
169次數大於一半才是眾數
思路:
- 設定maj和cnt變數
- 遍歷
- 如果cnt==0,那麼maj更新為當前num,cnt++,即初始化為1,否則如果重複,cnt++,不重複cnt--
int maj = 0, cnt = 0;
// 遍歷
for (int num : nums){
if (num == maj){
cnt++;
}
else if (cnt == 0) {
maj = num;
cnt++;
}
else cnt--;
}
229超過n/3屬於眾數
思路
- 和上面類似,但設定兩個候選眾數。而且要對這兩個候選變數進行驗證,即是否真的超過n/3
int m = 0, n = 0, cm = 0, cn = 0;
for (auto &a : nums) {
if (a == m) ++cm;
else if (a ==n) ++cn;
else if (cm == 0) m = a, cm = 1;
else if (cn == 0) n = a, cn = 1;
else --cm, --cn;
}
cm = cn = 0;
for (auto &a : nums) {
if (a == m) ++cm;
else if (a == n) ++cn;
}
if (cm > nums.size() / 3) res.push_back(m);
if (cn > nums.size() / 3) res.push_back(n);
return res;
238除自身以外陣列的乘積
輸入: [1,2,3,4]
輸出: [24,12,8,6]
思路:題目不能用除法
- 新建陣列記錄每個數字左邊的累積,然後乘上右邊的累乘。右邊的累乘用一個變量表示,不斷作用於儲存了左邊累積的陣列
- 注意邊界問題:左邊界初始化為1,右邊界記錄的是[0, n-2]的累積,所以不需要nums[n-1]
注意邊界初始化record[0] = 1和right = 1,再根據例子列出左累乘[1,1,2,6]就可已解出
int n = nums.length;
int[] record = new int[n];
record[0] = 1;
for (int i = 1; i < n; i++){
record[i] = record[i-1] * nums[i-1];
}
int right = 1;
for (int i = n - 1; i >=0; i--){
record[i] *= right;
right *= nums[i];
}
return record;
69Sqrt(x) 求平方根
if (x == 0) return 0;
double res = (double) x;
double last = 0.0;
while (res != last) {
last = res;
res = res - x / (2 * res); // 求解看下面
}
return (int) res;
f(x) = x^2^ - n
(f(x) - f(x~i~))/ (x - x~i~) = f'(x~i~)
求出x~i+1~ = g(x)即可,x表示上面res,f(x)表示上面的引數x
231Power of Two
n > 0 && (n & (n-1)) == 0