1. 程式人生 > >二分法快-LeetCode50-Pow(x, n)

二分法快-LeetCode50-Pow(x, n)

題目

實現 pow(x, n) ,即計算 x 的 n 次冪函式。

示例 1:

輸入: 2.00000, 10
輸出: 1024.00000
示例 2:

輸入: 2.10000, 3
輸出: 9.26100
示例 3:

輸入: 2.00000, -2
輸出: 0.25000
解釋: 2-2 = 1/22 = 1/4 = 0.25
說明:

-100.0 < x < 100.0
n 是 32 位有符號整數,其數值範圍是 [−231, 231 − 1] 。

思路1

普通思路,n個x相乘。超時。

程式碼1

class Solution {
    public double myPow(double x, int n) {
        if(n==0){
            return 1;
        }
        double res=0;
        if(n>0){
            res=x;
            for(int i=1;i<n;i++){
                res=res*x;
            }
        }else{
            n=-n;
            res=x;
            for(int i=1;i<n;i++){
                res=res*x;
            }
            res=1/res;
        }
        return res;
    }
}

思路2

翻倍。類似https://blog.csdn.net/qq_36025975/article/details/83685382。超時。

程式碼2

class Solution {
    public double myPow(double x, int n) {
        if(n==0){
            return 1;
        }
        if(x==1){
            return 1;
        }
        
        long nn=0;
        if(n>0){
            nn=n;
        }else{
            nn=-n;
        }
        
        double res=1;
        
        double mul=x;
        long count=1;
        while(true){
            if(nn==0){
                break;
            }
            if(count+count<nn){
                mul=mul*mul;
                count=count+count;
            }else{
                res=res*mul;
                
                nn=nn-count;
                mul=x;
                count=1;
            }
        }
        if(n<0){
            res=1/res;
        }
        return res;
    }
}

思路3

遞迴。二分。n個x相乘=(n/2個x相乘)X (n/2個x相乘)。

程式碼3

class Solution {
    public double myPow(double x, int n) {
        // 為防止溢位,使用long型別
        long nn=0;
        if(n==0){
            return 1;
        }else if(n>0){
            nn=(long)n;
        }else{
            // 有溢位可能,所以使用long型別
            nn=-(long)n;
        }
        
        double res=0;
        double myPow=myPow(x,(int)(nn/2));
        if(nn%2==0){
            // 這種寫法超時,應改為下面語句的寫法
            // res=myPow(x,(int)(nn/2)) * myPow(x,(int)(nn/2));
            res=myPow * myPow;
        }else{
            res=myPow * myPow * x;
        }
        
        if(n<0){
            res=1/res;
        }
        return res;
    }
}

關鍵

1.二分法快。

2.int有溢位可能時使用long。

3.

        double myPow=myPow(x,(int)(nn/2));
        if(nn%2==0){
            // 這種寫法超時,應改為下面語句的寫法
            // res=myPow(x,(int)(nn/2)) * myPow(x,(int)(nn/2));
            res=myPow * myPow;
        }else{
            res=myPow * myPow * x;
        }

4.思路2也是二分法但是需要多次使用二分,思路3二分法只需使用一次,所以思路2超時思路3不超時。