[js] 举例说明js中什么是尾调用优化
[js] 舉例說明js中什么是尾調用優化
上次介紹了什么是尾調用以及怎么準確快速的判別一個函數調用是否為尾調用。那么,我們判別尾調用的意義是什么呢?做什么事情總歸有個目的,那么今天我們就來系統的介紹一下尾調用的意義,或者說尾調用有什么用吧。
2. 尾調用優化
我們知道,函數的調用會在內存中生成一個“調用幀”(call frame),保存著函數的調用位置和內部變量等信息。如果在函數A的內部調用函數B,那么在A的調用幀上方還會生成一個B的調用幀。等到函數B運行結束,將結果返回到A,B的調用幀才會消失。如果函數B的內部還調用函數C,那么在B的調用幀上方又會生成一個C的調用幀,以此類推。所有的調用幀就形成了一個“調用棧”(call stack)。
我們知道,尾調用是函數的最后一步操作,外部函數的調用位置和其內部變量信息都不會再用到了,所以不需要保留外部函數的調用幀了,直接用內層函數的調用幀取代外層函數的調用幀即可。
如果所有的函數都是尾調用,那么完全可以做到每次執行時的調用幀只有一項,這將大大的節省內存,更不可能發生內存溢出,這就是討論尾調用的意義所在。
所謂的“尾調用優化”,其實就是保證在函數執行時只保留內層函數的調用幀,換句話說,就是用內層函數的調用幀取代外部函數的調用幀,即執行時內存中只保存一項調用幀。
3. 如何做到尾調用優化
通過上面的討論,我們知道了,只要外部函數的調用幀被內層函數的調用幀取代即可做到“尾調用優化”。同時,我們也知道調用幀是用來保存函數調用位置和內部變量信息的,所以,要想讓內層函數的調用幀取代外部函數的調用幀,只需要保證,在調用內層函數時,不再用到和外部函數有關的一切信息即可(不再用到外部函數的內部變量)。
如此,我們總結出只有內層函數在被調用時不再用到外部函數的內部變量,才能做到“尾調用優化”。
先來,看一個例子:
function f(a) {var b = 3;function g(n) {return n + b}return g(a) }上述例子,我們明顯可以看出這是典型的尾調用,那么這有沒有做到“尾調用優化”呢?很明顯,可以看出在調用內部函數g的時候,其內部用到外部函數f 的內部變量b,故在函數g 被調用時,g 的調用幀并不能取代外部函數f 的調用幀,所以這不是“尾調用優化”。
個人簡介
我是歌謠,歡迎和大家一起交流前后端知識。放棄很容易,
但堅持一定很酷。歡迎大家一起討論
主目錄
與歌謠一起通關前端面試題
總結
以上是生活随笔為你收集整理的[js] 举例说明js中什么是尾调用优化的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Java课程设计-学生成绩管理系统
- 下一篇: 飞机大战一Java课程设计