https://leetcode.cn/problems/powx-n/description/
實現 pow(x, n) ,即計算 x 的整數 n 次冪函數(即,xn )。
示例 1:
輸入:x = 2.00000, n = 10
輸出:1024.00000
示例 2:
輸入:x = 2.10000, n = 3
輸出:9.26100
示例 3:
輸入:x = 2.00000, n = -2
輸出:0.25000
解釋:2-2 = 1/22 = 1/4 = 0.25
提示:
-100.0 < x < 100.0
-2^31 <= n <= 2^31-1
n 是一個整數
要麼 x 不爲零,要麼 n > 0 。
-104 <= xn <= 104
解答
考慮冪指數過大,不可能暴力逐個乘下去。
使用快速冪手段來解決該題
我們求解2^7 是 2*2*2*2*2*2*2
注意到7的二進制是111,對應的 2^7 也可以表示成 2^1 * 2^2* 2^3 = 2*4*16
那麼暴力的逐個乘時間O(n) 可以優化成時間O(logn)
代碼如下
class Solution {
public:
double myPow(double x, int n) {
double ret = 1.0;
while(n>0){
if(n&1){
ret *=x;
}
n>>=1;
x*=x;
}
return ret;
}
};
注意版本1 並不能通過 n 有負數。
我們添加負數標記,計算完成後 結果result變成 1/result;
class Solution {
public:
double myPow(double x, int n) {
double ret = 1.0;
int flag =0;
if(n<0) {flag =1;n=-n;}
while(n>0){
if(n&1){
ret *=x;
}
n>>=1;
x*=x;
}
if(flag==1) ret = 1/ret;
return ret;
}
};
版本2很接近勝利了,但是n的範圍在計算+-n的時候已經超過int的最大值了。
使用longlong 解決,所以得出最後的正確版本
class Solution {
public:
double myPow(double x, int m) {
double ret = 1.0;
int flag =0;
long long n =m;
if(n<0) {flag =1;n=-n;}
while(n>0){
if(n&1){
ret *=x;
}
n>>=1;
x*=x;
}
if(flag==1) ret = 1/ret;
return ret;
}
};