斐波那契数列的js实现

5,378 阅读2分钟

1.什么是斐波那契数列

斐波那契数列(Fibonacci sequence) 又称黄金分割数列、因数学家列昂纳多·斐波那契(Leonardoda Fibonacci)以兔子繁殖为例子而引入,故又称为“兔子数列”,指的是这样一个数列:1、1、2、3、5、8、13、21、34、……在数学上,斐波那契数列以如下被以递推的方法定义:F(1)=1,F(2)=1, F(n)=F(n - 1)+F(n - 2)(n ≥ 3,n ∈ N*)

2.斐波那契数列的实现

2.1 递归

看到这个题目最容易想到的就是递归

let fib = function(n) {
    if(n <= 2) {
        return 1
    }
    return fib(n-2) + fib(n-1)
}

2.1.1 递归优化

如果是获取数列的某一项,上面的方法就够用了,但若是需要得到一个数列,那么很容易就能发现用上面的方法存在重复调用,因此可以用一个数组将前面的数据缓存起来

let memorize = [1,1]
let fib = function(n) {
    redo++
    if(!memorize[n-1]) {
        memorize[n-1] = fib(n-1) + fib(n-2)
    }
    return memorize[n-1]
}

2.2 尾递归调用

尾调用(Tail Call)是函数式编程的一个重要概念,本身非常简单,就是指某个函数的最后一步是调用另一个函数。

let fib = function(n, prev=1, next=1) {
    if(n <= 2) {
        return next
    }
    return fib(n-1, next, prev + next)
}

2.3 递推

上面的递归算法中我们获取某一项的值时是从后一步步往前推,现在我们换成从前往后推,即递推。既然三项中的前两项相加等于第三项,写成表达式就是res[i-2] + res[i-1] = res[i]

2.3.1 for循环

let fib = function(n) {
    if(n<=2) {
        return 1
    }
    let sum = 0
    let prev = 1
    let next = 1
    for(let i=3;i<=n;i++) {
        sum = prev + next
        prev = next
        next = sum
    }
    return sum
}

2.3.2 while

let fib = function(n) {
    let i = 2
    let res = [0,1,1]
    while(i <= n) {
        res[i] = res[i - 1] + res[i - 2]
        i++
    }
    return res[n]
}