歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
您现在的位置: Linux教程網 >> UnixLinux >  >> Linux編程 >> Linux編程

如何使用JavaScript書寫遞歸函數

遞歸函數大家都應該比較熟吧?那麼,如何在JavaScript中書寫一個完美的遞歸函數呢?且聽我娓娓道來。

遞歸函數

寫的時候,查了一下維基百科對遞歸函數的定義,恕我愚鈍,簡直太深奧了!所以,我還是簡單的說說我對遞歸函數的理解吧。遞歸函數,說白了就是在函數內部引用函數自身,最終到給定的遞歸結束條件時回溯。當然,你也可以不給定結束條件,死了別掛我~(╯﹏╰)~

使用javascript書寫遞歸函數

現在,一步一步,摩擦摩擦,在皎潔的編輯器上,來開始使用javascript寫遞歸函數吧!

function fun(num){
    if(num <= 1){
    return 1;
    } else{
    return num * fun(--num); 
    }
}

好了,不錯,一個堪稱經典的遞歸求階乘的函數誕生了。事情肯定不會這麼順利,一定是個圈套。我們來如下調用以下看看會怎麼樣?

var test = fun;
fun = null;
console.log(test(7));

呵呵,居然報錯了

Uncaught TypeError: object is not a function

嗯,報了類型錯誤。。。

回過頭去看看我們是如何調用的。發現問題了吧!我們把fun賦給了test,然後把fun給回收掉了。為什麼會出錯呢?因為像function這種賦值其實是引用傳遞,只是把指向函數的指針(這裡說地址也行)賦給test了。但我們把fun賦值為null的時候,函數都已經被回收了,拿什麼來執行?知道問題所在了,我決定換種方式來定義:

function fun(num){
    if(num <= 1){
    return 1;
    } else{
    return num * arguments.callee(--num); 
    }
}

然後測試一下:

var test = fun;
fun = null;
console.log(test(7));

OK,測試通過!

但是在某一天,當我實際碼代碼的時候,問題又出現了。什麼問題呢?我們來看一下:

Uncaught TypeError: 'caller', 'callee', and 'arguments' properties may not be accessed on strict mode functions or the arguments objects for calls to them 

╮(╯▽╰)╭哎!可憐啊!因為我使用了"use strict"!嚴格模式下是不允許的。。。

好吧!繼續想辦法!既然不能使用arguments.callee(),那還是想想其他的方式吧。

看下面的代碼:

var fun = (function f(num){
    if(num <= 1){
    return 1;
    } else{
    return num * f(--num); 
    }
});

然後我測試了以下,神奇的通過了,暫時沒有發現任何問題!

為什麼呢?因為我們使用了“()”,巧妙地使用命名函數表達式來達到了同樣的效果。

參考資料

《JavaScript高級程序設計(第三版)》 http://www.linuxidc.com/Linux/2014-09/107426.htm

 

Copyright © Linux教程網 All Rights Reserved