回覆列表
  • 1 # TonyDeng

    邏輯上是這樣,但實現不是。函式程式碼是隻有一份的,不會有複製品,所以每次都是執行同一份程式碼,這點是不變的,包括面向物件的類函式和方法,也是這樣,變的只是各種屬性,程式碼永遠只有一份,無論建立多少物件實體均是如此。遞迴的實現機制,是把引數依次壓棧,函式處理後壓入的引數,後入先出,回退時處理前面的引數,直到遞迴結束,這樣邏輯上看起來是每次不同的過程,但函式程式碼是不變的。

    遞迴的這種機制,弊端在棧上。棧容量是有限的,不會很大(棧並非僅僅容納這個遞迴過程所需引數,是整個程式共用的),如果遞迴的引數多、層次深,壓入全部的引數可能導致棧溢位。學院派很喜歡炫耀遞迴,但實操上需要慎用,濫用這個方法的程式設計師,不會是高手。遞迴完全可以轉換為迴圈實現,而且比遞迴高效,只是可讀性稍差,在追求效率的場合不要用遞迴。

  • 2 # 散居獵人

    遞迴就是直接或間接呼叫自己。

    學習程式設計語言,不需要我認為我覺得我理解。。。都是規定,遵守就是了。

    見過很多人費勁巴力學不好。。。老說我理解。。。不用你理解!程式語言就是個工具,你照說明書用就行了。

    少動腦筋才能學好程式語言,多動腦筋才能做好軟體開發。

  • 3 # 晨星4130

    遞迴函式就是呼叫自己,程式執行的函式是一樣的,只是每次呼叫都會分配新的棧內容,遞迴呼叫時一定要確保呼叫的終止條件,否則程式就掛了。

  • 4 # Cofire

    哦,這個...是不是走火入魔了,誤入歧途了!

    函式是不是呼叫自己,看呼叫的名稱。

    至於記憶體分配,資料變化,堆疊地址變化——不變化幹嘛還要遞迴呼叫?

  • 5 # 切問近思61177173

    遞迴有兩種方式實現,一種用系統堆疊,完全不管記憶體,每次呼叫就會生成一個新執行緒。一種用指標和本地堆疊保護斷點,迴圈往復呼叫一個執行緒。

  • 6 # IT人故事會

    你怎麼認為都可以,你沒走火入魔,只是想的太多了,你只要實現就可以了 ,不要管那麼多,書讀百遍其義自見,你現在讀的太少了,讀多了就行了。

  • 7 # 柳牧山

    遞迴呼叫也是一種函式呼叫,又分為自遞迴(同一函式自己呼叫自己)和互遞迴(不同函式之間互相呼叫形成遞迴)。

    程式執行過程中,函式的程式碼是固定的,不會有什麼變化,而相關資料會隨著每次呼叫時的環境變化而不同,因此係統對函式執行時相應的資料進行管理。

    象C、C++、Java等現代語言,每次函式呼叫時會申請一塊記憶體來記錄實參、區域性變數、臨時變數、返回地址等內容,退出時這塊記憶體會釋放掉。這樣就做到同一函式的呼叫沒有退出時又能啟動另一個呼叫,也就能支援函式的遞迴這樣的現代語言的特性。

  • 8 # 編碼之道

    從原理上來講這個問題會涉及到數學與計算機的理論知識,並且難以理解,還是讓我們以一個簡單的例項來說明。

    先看下面這個簡單的求階乘的程式,在計算5!的過程中,呼叫過程如下,可見fac函式雖然被呼叫了5次,但是每次傳入的引數都不一樣,返回的結果也各不相同。

    再讓我們看看這個遞迴程式在呼叫過程中的呼叫堆疊情況,選擇除錯模式,先在函式體內設定一個斷點,當程式停在斷點處時,可見呼叫堆疊中有5個fac函式,雙擊檢視每個fac函式呼叫時區域性變數情況,會發現每次的值與返回值都不一樣。參考下面影片:

    從上面例子可以看出,遞迴函式的每次呼叫都執行了同樣的程式碼,但是因為傳入的引數不一樣,嚴格來說可以認為這兩個函式不一樣,所以說不是呼叫自己也算正確,實際上如果兩個函式完全一樣的話,遞迴就會陷入死迴圈而無法結束,直到耗盡記憶體而崩潰。至於說是呼叫複製品,則不夠準確,因為函式的實現程式碼在計算機記憶體中只有一份,每次呼叫執行的都是同樣的程式碼,所以並不存在另一個複製品。

    那麼遞迴呼叫是怎麼實現的呢,實際上和一般的函式一樣,簡單來說就是把當前程式的狀態壓入堆疊(一種先進後出的資料結構),將引數放入特定的暫存器或者指定地址,然後跳轉到被呼叫函式的入口,函式執行結束後從堆疊中恢復上一個狀態,繼續執行原來的程式。

    最後對於遞迴函式有一點至關重要,那就是必須要有一個結束條件,並且是可達的,這樣遞迴才會結束。否則遞迴將陷入死迴圈,再看一個這樣的例子,現代編譯器很智慧,對於這樣的問題會給出警告,如果忽略該警告,繼續執行將會導致程式崩潰。

  • 中秋節和大豐收的關聯?
  • 託福口語緊張發揮不好怎麼辦?