-
遞歸算法
鎖定
- 屬 性
- 計算機算法
- 實現過程
- 一般通過函數或子過程來實現
- 特 點
- 遞歸就是在過程或函數里調用自身
遞歸算法簡介
遞歸算法應用的場景是要解決的問題和其子問題具有相似性的時候,通過直接或間接的調用自己求出問題解的方法。它是通過解決一個問題的更小實例來解決一個大的問題的解的算法。遞歸算法有兩個過程,一是調用過程,二是向上傳遞結果的過程。
[3]
遞歸算法遞歸程序
在支持自調用的編程語言中,遞歸可以通過簡單的函數調用來完成,如計算階乘的程序在數學上可以定義為:
(define (factorial n) (if (= n 0) 1 (* n (factorial (- n 1)))))
遞歸算法不動點組合子
即使一個編程語言不支持自調用,如果在這語言中函數是第一類對象(即可以在運行期創建並作為變量處理),遞歸可以通過不動點組合子(英語:Fixed-point combinator)來產生。以下Scheme程序沒有用到自調用,但是利用了一個叫做Z 算子(英語:Z combinator)的不動點組合子,因此同樣能達到遞歸的目的。
(define Z (lambda (f) ((lambda (recur) (f (lambda arg (apply (recur recur) arg)))) (lambda (recur) (f (lambda arg (apply (recur recur) arg)))))))(define fact (Z (lambda (f) (lambda (n) (if (<= n 0) 1 (* n (f (- n 1))))))))
這一程序思路是,既然在這裏函數不能調用其自身,可以用 Z 組合子應用(application)這個函數後得到的函數再應用需計算的參數。
遞歸算法尾部遞歸
尾部遞歸是指遞歸函數在調用自身後直接傳回其值,而不對其再加運算。尾部遞歸與循環是等價的,而且在一些語言(如Scheme中)可以被優化為循環指令。 因此,在這些語言中尾部遞歸不會佔用調用堆棧空間。以下Scheme程序同樣計算一個數字的階乘,但是使用尾部遞歸:
[1]
(define (factorial n) (define (iter product counter) (if (> counter n) product (iter (* counter product) (+ counter 1)))) (iter 1 1))
遞歸算法能夠解決的問題
- 數據的定義是按遞歸定義的。如Fibonacci函數。
- 問題解法按遞歸算法實現。如Hanoi問題。
- 數據的結構形式是按遞歸定義的。如二叉樹、廣義表等。
遞歸算法遞歸數據
data ListOfStrings = EmptyList | Cons String ListOfStrings
- 參考資料
-
- 1. Harold Abelson and Gerald Jay Sussman with Julie Sussman. Structure and Interpretation of Computer Programs. Cambridge, MA: MIT Press. 1996 [2011]. ISBN 0-262-01153-0
- 2. Graham, Ronald; Donald Knuth, Oren Patashnik. Concrete Mathematics. 1990. Chapter 1: Recurrent Problems
- 3. 胡昆鵬,仵子俊.分治遞歸算法的解題能力[J].電腦編程技巧與維護,2023(1):44-47
- 4. 張孟常.設計概論新編 增補版:上海人民美術出版社,2021.10:174
- 5. 喜超,高儼,譚雅青編著.C#面向對象程序設計:雲南科技出版社,2021.09:71