數據之間的相互關係稱爲邏輯結構。通常分爲四類基本結構:
集合 結構中的數據元素除了同屬於一種類型外,別無其它關係。
線性結構 結構中的數據元素之間存在一對一的關係。
樹型結構 結構中的數據元素之間存在一對多的關係。
圖狀結構或網狀結構 結構中的數據元素之間存在多對多的關係。
數據結構在計算機中有兩種不同的存儲方法:
順序存儲結構:用數據元素在存儲器中的相對位置來表示數據元素之間的邏輯關係。
鏈式存儲結構:在每一個數據元素中增加一個存放地址的指針,用此指針來表示數據元素之間的邏輯關係。
時間複雜度
一個算法花費的時間與算法中語句的執行次數成正比例,哪個算法中語句執行次數多,它花費時間就多。一個算法中的語句執行次數稱爲語句頻度或時間頻度。記爲T(n)
在剛纔提到的時間頻度中,n稱爲問題的規模,當n不斷變化時,時間頻度T(n)也會不斷變化。但有時我們想知道它變化時呈現什麼規律。爲此,我們引入時間複雜度概念。
一般情況下,算法中基本操作重複執行的次數是問題規模n的某個函數,用T(n)表示,若有某個輔助函數f(n),使得當n趨近於無窮大時,T(n)/f(n)的極限值爲不等於零的常數,則稱f(n)是T(n)的同數量級函數。記作T(n)=O(f(n)),稱O(f(n)) 爲算法的漸進時間複雜度,簡稱時間複雜度。
有時候,算法中基本操作重複執行的次數還隨問題的輸入數據集不同而不同,如在冒泡排序中,輸入數據有序而無序,其結果是不一樣的。此時,我們計算平均值。
常見的算法的時間 複雜度之間的關係爲:
O(1)<O(logn)<O(n)<O(nlog n)<O(n2)<O(2n)<O(n!)<O(nn)
實例1
- sum=0; //(1)
- for(i=1;i<=n;i++) //(2)
- for(j=1;j<=n;j++) //(3)
- sum++; //(4)
語句(1)執行1次,
語句(2)執行n次
語句(3)執行n2次
語句(4)執行n2次
T(n) = 1+n+2n2= O(n2)
實例2
- a=0; b=1; //(1)
- for (i=1;i<=n;i++) //(2)
- {
- s=a+b; //(3)
- b=a; //(4)
- a=s; //(5)
- }
語句(1)執行1次,
語句(2)執行n次
語句(3)、(4)、(5)執行n次
T(n) = 1+4n =O(n)
實例3
- i=1; //(1)
- while (i<=n)
- i=i*2; //(2)
語句(1)的頻度是1,
設語句2的頻度是f(n),則:2f(n)<=n;f(n)<=log2n
取最大值f(n)= log2n,
T(n)=O(log2n )
空間複雜度
空間複雜度:算法所需存儲空間的度量,記作:
S(n)=O( f(n) )
其中 n 爲問題的規模。
一個算法在計算機存儲器上所佔用的存儲空間,包括存儲算法本身所佔用的存儲空間,算法的輸入輸出數據所佔用的存儲空間和算法在運行過程中臨時佔用的存儲空間這三個方面。如果額外空間相對於輸入數據量來說是個常數,則稱此算法是原地工作。
算法的輸入輸出數據所佔用的存儲空間是由要解決的問題決定的,是通過參數表由調用函數傳遞而來的,它不隨本算法的不同而改變。存儲算法本身所佔用的存儲空間與算法書寫的長短成正比,要壓縮這方面的存儲空間,就必須編寫出較短的算法。