漢諾塔層數大於10時輸出不正常的分析及時間複雜度
阿新 • • 發佈:2019-01-28
使用遞迴方式解決漢諾塔問題,具體思路就不詳細敘述了,程式碼如下:
#include <iostream> using namespace std; int i; void moveDisk(int diskNum, char from, char to, char aux) { if(diskNum == 1){ cout << "step" << ++i << ": "; cout << "Move disk1 from " << from << " to " << to << "\n"; } else{ moveDisk(diskNum - 1, from, aux, to); cout << "step" << ++i << ": "; cout << "Move disk" << diskNum << " from " << from << " to " << to << "\n"; moveDisk(diskNum - 1, aux, to, from); } } int main() { int init; cin >> init; moveDisk(init, 'A', 'C', 'B'); return 0; }
自己在執行時,發現了這樣的問題,當輸入層數init大於等於10時,命令列輸出中沒有大於等於10的盤號!一開始以為是實現思路有問題,但反覆思考幾遍並沒有發現問題,然後我認為可能編譯器對巢狀層數有要求,當層數太大時,超過了規定巢狀層數而導致輸出錯誤,按照這一思路查詢相關資訊,發現應該不是這個原因,編譯器對巢狀層數一般沒有要求,可能出現錯誤的情況是巢狀層數太深導致堆疊溢位,而10層的漢諾塔求解是不可能讓堆疊溢位的。
後來通過給每行輸出加上步驟號(本來沒有步驟號),發現原來命令列儲存的行數是有限制的,大於10的盤號被頂上去了未能顯示出來。。。
最後分析一下使用遞迴的方法解決漢諾塔問題的時間複雜度:
令盤數為n,執行次數為f(n),
當n=1時,f(1)=1;
當n=2時,f(2)=2*f(1)+1=3;
當n=3時,f(3)=2*f(2)+1=7;
.........
當n=n時,f(n)=2*f(n-1)+1;
由上面的公式變形可得f(n)+1=2[f(n-1)+1],則f(n)+1=2^2*[f(n-2)+1]=...=2^(n-1)*[f(1)+1]=2^n,
則f(n)=2^n-1,按照O階的寫法,複雜度為O(2^n)。