計算斐波那契數列

斐波那契數列的詳細定義可以查看斐波那契數列

看一些算法書,提到遞歸,經常會拿斐波那契數列來舉例,所以今天就寫點程序,簡單討論一下。

這裏包括了兩個方法,一個是遞歸計算,效率極其低下;另一種,就是直接利用循環計算,效率是就好很多,下面是代碼:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Diagnostics;

namespace FibonacciNumber
{
    class Program
    {
        // F(0) = F(1) = 1, F(n) = F(n-1) + F(n-2) (n>=2)
        static void Main(string[] args)
        {
            Console.WriteLine("N\tValue\tCost(ms)");
            for (ulong i = 1; i <= 50; ++i)
            {
                KeepTime(FibonacciNonRecursive, i);
            }

            Console.WriteLine("N\tValue\tCost(ms)");
            for (ulong i = 1; i <= 50; ++i)
            {
                KeepTime(FibonacciRecursive, i);
            }
        }

        static void KeepTime(Func<ulong, ulong> action, ulong index)
        {
            ulong value = 0;
            Stopwatch time = new Stopwatch();
            time.Start();
            value = action(index);
            time.Stop();
            Console.WriteLine("{0}\t{1}\t{2}", index, value, time.ElapsedMilliseconds);
        }

        // Calculate Fibonacci Number recursively
        static ulong FibonacciRecursive(ulong n)
        {
            if (n <= 1)
            {
                return 1;
            }
            else
            {
                return FibonacciRecursive(n - 1) + FibonacciRecursive(n - 2);
            }
        }

        // Calculate Fibonacci Number non-recursively
        static ulong FibonacciNonRecursive(ulong n)
        {
            if (n <= 1)
            {
                return 1;
            }
            else
            {
                ulong minusOne = 1;
                ulong minusTwo = 1;
                ulong value = 0;
                for (ulong i = 2; i <= n; ++i)
                {
                    value = minusOne + minusTwo;
                    minusTwo = minusOne;
                    minusOne = value;
                }
                return value;
            }
        }
    }
}

FibonacciRecursive方法是遞歸算法
FibonacciNonRecursive方法是非遞歸算法

下面是兩個方法計算前50個數的時間:

N Value FibonacciNonRecursive Cost(ms) FibonacciRecursive Cost(ms)
1 1 0 0
2 2 0 0
3 3 0 0
4 5 0 0
5 8 0 0
6 13 0 0
7 21 0 0
8 34 0 0
9 55 0 0
10 89 0 0
11 144 0 0
12 233 0 0
13 377 0 0
14 610 0 0
15 987 0 0
16 1597 0 0
17 2584 0 0
18 4181 0 0
19 6765 0 0
20 10946 0 0
21 17711 0 0
22 28657 0 0
23 46368 0 0
24 75025 0 1
25 121393 0 2
26 196418 0 4
27 317811 0 6
28 514229 0 11
29 832040 0 18
30 1346269 0 29
31 2178309 0 47
32 3524578 0 77
33 5702887 0 122
34 9227465 0 199
35 14930352 0 324
36 24157817 0 526
37 39088169 0 857
38 63245986 0 1390
39 102334155 0 2267
40 165580141 0 3668
41 267914296 0 5902
42 433494437 0 9505
43 701408733 0 15374
44 1134903170 0 24746
45 1836311903 0 39804
46 2971215073 0 64230
47 4807526976 0 103802
48 7778742049 0 168007
49 12586269025 0 271728
50 20365011074 0 439400

從上圖可以看出,非遞歸方法非常快,時間複雜度是線性的,而遞歸方法,則要慢很多,基本感覺是指數級增長


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章