爬樓梯

題目

來源:力扣(LeetCode)
鏈接:爬樓梯

思路一 暴力搜索

暴力搜索,題目可以轉換爲整數n可以拆成a個1和b個2相加 這種拆法有多少種 ,且4=1+2+14=1+2+14=2+1+14=2+1+1是不同的拆法。
由於每踏一步有兩種選法,至少需要篩選n次,所以時間複雜度約爲o(2n)但這種做法會超時。

代碼

void dfs(int sum,int n,int *cnt){
    if(sum==n){
        (*cnt)++;
        return;
    }
    if(sum>n){
        return;
    }
    for(int i=1;i<=2;i++){
        dfs(sum+i,n,cnt);
    }
}

int climbStairs(int n){
    int cnt=0;
    dfs(0,n,&cnt);
    return cnt;
}

思路二 轉換爲斐波那契數

爬到第n層的有幾張走法可以等價於爬到n-1層的走法加爬到n-2的走法。
f(n)=f(n1)+f(n2)f(0)=1,f(1)=1f(n)=f(n-1)+f(n-2),f(0)=1,f(1)=1符合斐波那契數的特點。

求斐波那契數可以用以下方法

  1. 遞歸法優化,使用一維數組暫存中間結果
  2. 動態規劃求斐波那契數

遞歸法優化

如下圖,以n=5爲例,在計算f(5)時f(3)已經計算過,不需重複計算,返回數組元素fib[3]即可
在這裏插入圖片描述
代碼

int Fib(int i,int* fib){
    if(i==0||i==1){
        return 1;
    }
    if(fib[i]>0){
        return fib[i];
    }
    fib[i]=Fib(i-1,fib)+Fib(i-2,fib);
    return fib[i];
}
int climbStairs(int n){
    int fib[10000000];
    fib[0]=1;fib[1]=1;
    return Fib(n,fib);
}

動態規劃
初始狀態爲dp[0]=1,dp[1]=1dp[0]=1,dp[1]=1
動態轉移方程爲
dp[i]=dp[i1]+dp[i2] 爲dp[i]=dp[i-1]+dp[i-2]

代碼



int climbStairs(int n){
    int *dp=(int*)malloc(sizeof(int)*(n+1));
    
    dp[0]=1;
    dp[1]=1;
    for(int i=2;i<=n;i++){
        dp[i]=dp[i-1]+dp[i-2];
    }
    int res=dp[n];
    free(dp);
    return res;
}
發佈了38 篇原創文章 · 獲贊 13 · 訪問量 4015
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章