1 數(shù)組
數(shù)組是一組偶對(下標(biāo)值,數(shù)據(jù)元素值)的集合。在數(shù)組中,對于一組有意義的下標(biāo),都存在一個與其對應(yīng)的值。一維數(shù)組對應(yīng)著一個下標(biāo)值,二維數(shù)組對應(yīng)著兩個下標(biāo)值,如此類推。
數(shù)組是由 n(n>1)個具有相同數(shù)據(jù)類型的數(shù)據(jù)元素組成的有序序列,且該序列必須存儲在一塊地址連續(xù)的存儲單元中。
數(shù)組中的數(shù)據(jù)元素具有相同數(shù)據(jù)類型。
數(shù)組是一種隨機(jī)存取結(jié)構(gòu),給定一組下標(biāo),就可以訪問與其對應(yīng)的數(shù)據(jù)元素。
數(shù)組中的數(shù)據(jù)元素個數(shù)是固定的。
計算機(jī)的內(nèi)存結(jié)構(gòu)是一維(線性)地址結(jié)構(gòu),對于多維數(shù)組,將其存放(映射)到內(nèi)存一維結(jié)構(gòu)時,有個次序約定問題。即必須按某種次序?qū)?shù)組元素排成一列序列,然后將這個線性序列存放到內(nèi)存中。
二維數(shù)組是最簡單的多維數(shù)組,以此為例說明多維數(shù)組存放(映射)到內(nèi)存一維結(jié)構(gòu)時的次序約定問題。
對于,通常有兩種順序存儲方式
(1) 行優(yōu)先順序(Row Major Order) :將數(shù)組元素按行排列,第 i+1個行向量緊接在第 i 個行向量后面。對二維數(shù)組,按行優(yōu)先順序存儲的線性序列為:
PASCAL、C 是按行優(yōu)先順序存儲的。
(2) 列優(yōu)先順序(Column Major Order) :將數(shù)組元素按列向量排列,第 j+1 個列向量緊接在第 j 個列向量之后,對二維數(shù)組,按列優(yōu)先順序存儲的線性序列為:
FORTRAN 是按列優(yōu)先順序存儲的。
設(shè)有二維數(shù)組,若每個元素占用的存儲單元數(shù)為L個,
表示元素
的首地址,即數(shù)組的首地址
(1)以“行優(yōu)先順序”存儲
第 1 行中的每個元素對應(yīng)的(首)地址是:
第 m 行中的每個元素對應(yīng)的(首)地址是:
(2)以“列優(yōu)先順序”存儲
(1) 第 1 列中的每個元素對應(yīng)的(首)地址是:
(3) 第 n 列中的每個元素對應(yīng)的(首)地址是:
2 特殊矩陣
特殊矩陣(對稱矩陣,對角矩陣,三角矩陣)壓縮存儲:
多個相同的非零元素只分配一個元素值的存儲空間;
零元素不分配空間。
(1)對稱矩陣
對稱矩陣的特點(diǎn)是:在一個 n 階方陣中,有,其中 1≤i,j≤n,對稱矩陣關(guān)于主對角線對稱,因此只需存儲上三角或下三角部分即可。
設(shè)有對稱矩陣A[i][j]如下圖示:
存儲此二維數(shù)組,需要 n*n 個存儲單元。若只對下三角部分以行為主序順序存儲到一個向量中去,在下三角中共有個元素,壓縮存儲后的結(jié)果如下:
以一維數(shù)組 sa[n(n+1)/2]作為 n 階對稱矩陣 A 的存儲結(jié)構(gòu),則 sa[k]和矩陣元
(2)三角矩陣
①下三角矩陣:
設(shè)有下三角矩陣 A[i][j]如下圖所示:
在下三角矩陣中,主對角線以上的元素是一個常量。存完下三角中的元素之后,緊接著存儲對角線上方的常量,因?yàn)槭峭粋€常數(shù),所以存一個即可,其壓縮存儲后如下圖所示:
共存儲了 n(n+1)/2 個元素,設(shè)存入向量 SA=[k]中,這種存儲方式可節(jié)約個存儲單元,K與 i,j 的對應(yīng)關(guān)系為:
②上三角矩陣
設(shè)有上三角矩陣 A[i][j]如下圖所示:
在上三角矩陣中, K 與 i,j 的對應(yīng)關(guān)系為:
(3)對角矩陣
對角矩陣也稱為帶狀矩陣,如下圖所示:
在這種三對角矩陣中,所有非零元素都集中在以主對角線為中心的對角區(qū)域中,即除了主對角線和它的上下方若干條對角線的元素外,所有其他元素都為零(或同一個常數(shù) C)。
對角矩陣 A 也可以采用壓縮存儲,將三對角矩陣壓縮到向量 SA[k]中去,按以行為主序,順序的存儲其非零元素,按其壓縮規(guī)律,找到相應(yīng)的映象函數(shù)。k與i,j的對應(yīng)關(guān)系為:
3 稀疏矩陣
稀疏矩陣:設(shè)矩陣 A 是一個 n*m 的矩陣中有 s 個非零元素,設(shè) δ=s/(nm),稱δ為稀疏因子,如果某一矩陣的稀疏因子δ滿足δ≦0.05 時稱為稀疏矩陣。對于稀疏矩陣,采用壓縮存儲方法時,只存儲非 0 元素。必須存儲非 0 元素的行下標(biāo)值、列下標(biāo)值、元素值。
一個三元組
( (1,2,12), (1,3,9), (3,1,-3), (3,8,4), (4,3,24), (5,2,18), (6,7,-7), (7,4,-6) )
(1)三元組順序表
若以行序?yàn)橹餍颍∈杈仃囍兴蟹?0 元素的三元組,就可以得構(gòu)成該稀疏矩陣的一個三元組順序表。相應(yīng)的數(shù)據(jù)結(jié)構(gòu)定義如下:
#define MAX_SIZE 101
typedef int elemType;
typedef struct {//三元組結(jié)點(diǎn)定義
int row;/* 行下標(biāo) */
int col; /* 列下標(biāo) */
elemType value;/* 元素值 */
} Triple;
typedef struct {//三元組順序表定義
int rn;/* 行數(shù) */
int cn;/* 列數(shù) */
int tn;/* 非0元素個數(shù) */
Triple data[MAX_SIZE];
} TMatrix;
(2)十字鏈表
對于稀疏矩陣,當(dāng)非 0 元素的個數(shù)和位置在操作過程中變化較大時,采用鏈?zhǔn)酱鎯Y(jié)構(gòu)表示比三元組的線性表更方便。
矩陣中非 0 元素的結(jié)點(diǎn)所含的域有:行、列、值、行指針(指向同一行的下一個非 0 元)、 列指針(指向同一列的下一個非 0 元)。其次,十字交叉鏈表還有一個頭結(jié)點(diǎn),結(jié)點(diǎn)的結(jié)構(gòu)如圖所示。
由定義知,稀疏矩陣中同一行的非 0 元素的由 right 指針域鏈接成一個行鏈表,由 down指針域鏈接成一個列鏈表。則每個非 0 元素既是某個行鏈表中的一個結(jié)點(diǎn),同時又是某個列鏈表中的一個結(jié)點(diǎn),所有的非 0 元素構(gòu)成一個十字交叉的鏈表。稱為十字鏈表。
此外,還可用兩個一維數(shù)組分別存儲行鏈表的頭指針和列鏈表的頭指針。
typedef struct Clnode {
int row, col; /* 行號和列號 */
elemType value; /* 元素值 */
struct Clnode *down, *right;
} OLNode;/* 非 0 元素結(jié)點(diǎn) */
typedef struct {
int rn;/* 矩陣的行數(shù) */
int cn;/* 矩陣的列數(shù) */
int tn;/* 非0元素總數(shù) */
OLNode *rhead;
OLNode *chead;
} CrossList;
4 廣義表
廣義表是線性表的推廣和擴(kuò)充,在人工智能領(lǐng)域中應(yīng)用十分廣泛。
把線性表定義為 n(n≧0 )個元素 a1, a2 ,..., an 的有窮序列,該序列中的所有元素具有相 同的數(shù)據(jù)類型且只能是原子項(xiàng)(Atom)。所謂原子項(xiàng)可以是一個數(shù)或一個結(jié)構(gòu),是指結(jié)構(gòu)上不 可再分的。若放松對元素的這種限制,容許它們具有其自身結(jié)構(gòu),就產(chǎn)生了廣義表的概念。
廣義表(Lists,又稱為列表 ):是由 n(n ≧0)個元素組成的有窮序列: LS=其中
或者是原子項(xiàng),或者是一個廣義表。LS是廣義表的名字,n 為它的長度。若
是廣義表,則稱為 LS 的子表。習(xí)慣上:原子用小寫字母,子表用大寫字母。
若廣義表 LS 非空時:
(表中第一個元素)稱為表頭; 其余元素組成的子表稱為表尾;
。 廣義表中所包含的元素(包括原子和子表)的個數(shù)稱為表的長度。
廣義表中括號的最大層數(shù)稱為表深 (度)。
兩個基本操作 GetHead() GetTail()。
廣義表的重要結(jié)論:
(1) 廣義表的元素可以是原子,也可以是子表,子表的元素又可以是子表, ...。即廣義 表是一個多層次的結(jié)構(gòu)。
(2) 廣義表可以被其它廣義表所共享,也可以共享其它廣義表。廣義表共享其它廣義表 時通過表名引用。
(3) 廣義表本身可以是一個遞歸表。
(4) 根據(jù)對表頭、表尾的定義,任何一個非空廣義表的表頭可以是原子,也可以是子表, 而表尾必定是廣義表。