1. 程式人生 > 其它 >複雜度分析01:簡單的複雜度分析

複雜度分析01:簡單的複雜度分析

大O的定義

n表示資料規模,O(f(n))表示執行演算法所需要執行的指令數,和f(n)成正比

複雜度描述的是隨著資料規模n的增大,演算法效能的變化趨勢,在複雜度分析中,常數不重要一般忽略

時間複雜度 所需指令數(abcd為常數)
二分查詢法 O(logn) a*logn
尋找陣列中的最值 O(n) b*n
歸併排序法 O(nlogn) c*nlogn
選擇排序法 O(n^2) d*n^2

一個時間複雜度的問題

有一個字串陣列,將陣列中的每一個字串按照字母序排序;之後再將整個字串陣列按照字典序排序,這個過程的時間複雜度是多少?

每個字串的長度和字串陣列的長度沒有聯絡,需要分開計算

假設最長的字串長度為s,陣列的長度為n

則對每個字串排序的複雜度為O(slogs),總共為O(nslogs)

而對整個字串陣列排序時,比較兩個字串的順序,複雜度為O(s)而不是O(1),總共為O(snlogn)

故整個過程的時間複雜度為O(nslogns)

特殊用例下的時間複雜度

插入排序法時間複雜度為O(n^2),快速排序法時間複雜度為O(nlogn)

但是當測試用例完全有序時,插入排序法會升為O(n),而快速排序法會降為O(n^2)

資料規模的概念

對於一個O(n)級別的演算法,在不同資料規模下執行耗費的時間,如果想要在1s之內完成運算,O(n)演算法的規模大概為10^8

O(nlogn)演算法的規模大概為10^7

而O(n^2)演算法的規模只能有10000

因此可以根據資料規模的要求,選擇設計複雜度不同的演算法

資料規模 消耗時間
10^3 2.5e-06 s
10^4 2.5e-05 s
10^5 0.00025 s
10^6 0.0025 s
10^7 0.025 s
10^8 0.25 s
10^9 2.5 s
public class Algorithm {

    public static void main(String[] args) {

        long start = System.nanoTime();
        int sum = 0;

        for (int i = 0; i < 1000000000; i++) {
            sum += i;
        }

        long end = System.nanoTime();

        System.out.println((end - start) / 1000000000.0 + "s");
    }
}