![數(shù)據(jù)結(jié)構(gòu)與算法第6章圖結(jié)構(gòu)pot_第1頁(yè)](http://file4.renrendoc.com/view8/M00/23/1A/wKhkGWcsS0uACN90AAEKQ3bjS-4730.jpg)
![數(shù)據(jù)結(jié)構(gòu)與算法第6章圖結(jié)構(gòu)pot_第2頁(yè)](http://file4.renrendoc.com/view8/M00/23/1A/wKhkGWcsS0uACN90AAEKQ3bjS-47302.jpg)
![數(shù)據(jù)結(jié)構(gòu)與算法第6章圖結(jié)構(gòu)pot_第3頁(yè)](http://file4.renrendoc.com/view8/M00/23/1A/wKhkGWcsS0uACN90AAEKQ3bjS-47303.jpg)
![數(shù)據(jù)結(jié)構(gòu)與算法第6章圖結(jié)構(gòu)pot_第4頁(yè)](http://file4.renrendoc.com/view8/M00/23/1A/wKhkGWcsS0uACN90AAEKQ3bjS-47304.jpg)
![數(shù)據(jù)結(jié)構(gòu)與算法第6章圖結(jié)構(gòu)pot_第5頁(yè)](http://file4.renrendoc.com/view8/M00/23/1A/wKhkGWcsS0uACN90AAEKQ3bjS-47305.jpg)
版權(quán)說(shuō)明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)
文檔簡(jiǎn)介
救據(jù)輅相易算該
2褂;刻帶不
___第念*圖轄構(gòu)____
7、囹的基域概念
久畫的商儲(chǔ)方法
品囹的遍歷
么眩感樹(shù)和景小眩感樹(shù)
5、1向無(wú)環(huán)困及其應(yīng)用
6、獴短路往
1、囹的基本就念
7,7二天樹(shù)的定義
1、圖的定義
圖(Graph)由一個(gè)頂點(diǎn)集合Vn和一個(gè)邊(或者弧)集合En組成
,通常記為:G=(Vn,En),其中Vn中有n(n>0)個(gè)頂點(diǎn),E”中有e(
e>=0)條邊,且每一條邊都依附于V。中的兩個(gè)頂點(diǎn)看,寸(i,
j=l,2,---,n),該邊用頂點(diǎn)偶對(duì)來(lái)表示,記為(vj)。
圖6-1給出了一個(gè)圖的示例:
頂點(diǎn)集合:N={vl,v2,v3,v4,v5};
邊集合:E={(vl,v2),(vl,v4),(v2,v3),(v3,v4),
(v3,v5),(v2,v5)}
2.圖的相關(guān)術(shù)語(yǔ)》
⑴無(wú)命蹲
⑵有向圖
有向圖的邊用<Vj,Vj>表示;
v%,Vj>和<VjM>不是同一條邊;
有向邊也稱為弧,箭頭一端成為弧頭,另一端為弧尾。
例:圖6-2所示是一個(gè)有向圖G2。
表示為:
G2=(V2?E2)
V2={%"2尹3尹4}圖6-2有向圖G2
E2={<vt,v2>,<v1v3>,<v3,v4>,<v4,v1>}
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義4
(3)鄰接點(diǎn)、鄰接邊
(4)完全圖
⑸稠密圖、稀疏圖
⑹頂點(diǎn)的度、入度、出度
⑺邊的權(quán)、網(wǎng)圖
(8)路徑和路徑長(zhǎng)度
(9)回路、簡(jiǎn)單路徑、簡(jiǎn)單回路
(10)子圖
(11)連通的、連通圖、連通分量
(12)強(qiáng)連通圖、強(qiáng)連通分量
(13)連通圖(或子圖)的生成樹(shù)
(14)非連通圖的生成森林
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義5
7,2囹的基本據(jù)作
(1)CreatGraph(G):建立圖G的存儲(chǔ)。
⑵DestroyGraph(G):釋放圖G占用的存儲(chǔ)空間。
(3)GetVex(G,v):在圖G中找到頂點(diǎn)v,并返回頂點(diǎn)v的相關(guān)信息。
(4)PutVex(G,v,value):在圖G中找到頂點(diǎn)v,并將value值賦給頂
點(diǎn)V。
⑸InscrtVcx(G,v):在圖G中增添新頂點(diǎn)V。
(6)DeleteVex(G,v):在圖G中,刪除頂點(diǎn)v以及所有和頂點(diǎn)v相關(guān)
聯(lián)的邊或弧。
⑺InscrtArc(G,v,w):在圖G中增添一條從頂點(diǎn)v到頂點(diǎn)w的邊或弧
°2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義6
(8)DeleteArc(G,v,w):在圖G中刪除一條從頂點(diǎn)v到頂點(diǎn)w的邊或
弧。
(9)Traverse(G,v):在圖G中,從頂點(diǎn)v出發(fā)遍歷圖G。
(10)LocateVex(G,u):在圖G中找到頂點(diǎn)u,返回該頂點(diǎn)在圖中存
儲(chǔ)位置。
(11)FirstAdjVex(G,v):在圖G中,返回v的第一個(gè)鄰接點(diǎn)。若頂點(diǎn)
在G中沒(méi)有鄰接點(diǎn),則返回“空”。
(12)NextAdjVex(G,v,w):在圖G中,返回v的(相對(duì)于w的)下一
個(gè)鄰接點(diǎn)。若W是V的最后一個(gè)鄰接點(diǎn),則返回“空”。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義7
__蝎
需要注意的是:
在一個(gè)圖中,頂點(diǎn)是沒(méi)有先后次序的,但當(dāng)我們?cè)趯?duì)它的
存儲(chǔ)中確定了頂點(diǎn)的次序后,存儲(chǔ)中的頂點(diǎn)次序構(gòu)成了頂點(diǎn)之
間的相對(duì)次序。同樣的道理,對(duì)一個(gè)頂點(diǎn)的鄰接點(diǎn),也根據(jù)存
儲(chǔ)順序決定了第1個(gè)、第2個(gè)…。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義8
久畫的存儲(chǔ)方法
2/鄰接矩陣
1、鄰接矩陣的存儲(chǔ)思想
⑴圖中頂點(diǎn)順序存儲(chǔ);
⑵用一個(gè)n*n矩陣(設(shè)圖有n個(gè)頂點(diǎn))來(lái)存儲(chǔ)任意兩個(gè)頂
點(diǎn)之間邊的信息,也就是各頂點(diǎn)之間的鄰接關(guān)系。
1若(%,Vj)或<Vj,Vj>是E(G)中的邊
A[i]O]={
0若(v/j)或<%,3>不是E(G)中的邊
若G是帶權(quán)圖,則鄰接矩陣可定義為:
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義9
二/亞若(v/j)或v%,Vj>是E(G)中的邊
00
?;蛉?vi,v.)或v>不是E(G)中的邊
■其中,Wjj表示邊(胃*)或<%,¥>上的權(quán)值;8表示一個(gè)計(jì)算
機(jī)允許的、大于所有邊上權(quán)值的數(shù)。
用鄰接矩陣表示法表示的無(wú)向圖和網(wǎng)圖如下圖所示。
010r
A=1011
0100
JI00
f無(wú)向圖的鄰轆陣表示
「OO
963OO
9OO45OO
A=64OOOO7
35OOOO8
ipoOO78OO
Y網(wǎng)卻於陵矩陣表示
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義11
2、鄰接矩陣的表示
一用一個(gè)一維數(shù)組來(lái)存儲(chǔ)頂點(diǎn)信息;¥>
用一個(gè)二維數(shù)組存儲(chǔ)鄰接矩陣,用于表示頂點(diǎn)間相鄰關(guān)系;
⑴一般情況
若圖的頂點(diǎn)個(gè)數(shù)和邊的個(gè)數(shù)是一個(gè)變量時(shí),還需要留有足
夠的空間。故可將其形式描述如下:
#defineMaxVertexNum…/*定義能存儲(chǔ)的足夠大的頂點(diǎn)個(gè)數(shù)*/
typedefcharVertexType;/*VcrtcxType為頂點(diǎn)類型,設(shè)為字符型*/
typedefintEdgeType;/*EdgeType為邊的權(quán)值類型,設(shè)為整型*/
typedefstruct
{VertexTypevexs[MaxVertexNum];/*頂點(diǎn)表*/
EdgeTypeedges[MaxVertexNum][MaxVertexNum];/*eF接矩陣*/
intn,e;/*實(shí)際的頂點(diǎn)數(shù)和邊數(shù)*/
JMMGagh;數(shù)據(jù)結(jié)構(gòu)講義12
⑵簡(jiǎn)單情況
在大部分的應(yīng)用中,圖中的頂點(diǎn)個(gè)數(shù)和邊的個(gè)數(shù)常常是一個(gè)
已知的常量,不妨設(shè)為N和E,在這種情況下可以簡(jiǎn)化以上定義
為:
typedefcharVertexType;
typedefintEdgeType;
typedefstruct
{VertexTypevexs[N];/*頂點(diǎn)表*/
EdgeTypeedges[N][N];/*?F接矩陣*/
}MGragh;/*MGragh是以鄰接矩陣存儲(chǔ)的圖類型*/
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義13
一—_____._——.-—?
3、鄰接矩陣存儲(chǔ)方法的特點(diǎn)
①無(wú)向圖的鄰接矩陣一定是一個(gè)對(duì)稱矩陣。因此,在具體存放
鄰接矩陣時(shí)只需存放上(或下)三角矩陣的元素即可。
②對(duì)于無(wú)向圖,鄰接矩陣的第i行(或第i列)非零元素(或非8
元素)的個(gè)數(shù)正好是第i個(gè)頂點(diǎn)的度TD(v)。
③對(duì)于有向圖,鄰接矩陣的第i行(或第i列)非零元素(或非8
元素)的個(gè)數(shù)正好是第i個(gè)頂點(diǎn)的出度OD(v)(或入度ID(v))o
④用鄰接矩陣方法存儲(chǔ)圖,很容易確定圖中任意兩個(gè)頂點(diǎn)之間
是否有邊相連;但是,要確定圖中有多少條邊,則必須按行、
按列對(duì)每個(gè)元素進(jìn)行檢測(cè),所花費(fèi)的時(shí)間代價(jià)很大。這是用鄰
接矩陣存儲(chǔ)圖的局限性。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義14
4、需要說(shuō)明以下兩點(diǎn).一
(1)在圖中沒(méi)有一個(gè)特殊的頂點(diǎn)是“第一個(gè),第二個(gè)
…”,因此存儲(chǔ)時(shí)也是如此,頂點(diǎn)的存儲(chǔ)順序可以依實(shí)際問(wèn)
題的某個(gè)順序人為的來(lái)規(guī)定,一旦頂點(diǎn)的存儲(chǔ)順序確定,就
構(gòu)成了頂點(diǎn)之間的相對(duì)次序,鄰接矩陣一定要與其對(duì)應(yīng),除
了頂點(diǎn)數(shù)組的每個(gè)分量中的頂點(diǎn)信息域中存放的是頂點(diǎn)的信
息,其它地方存放的都是頂點(diǎn)的存儲(chǔ)序號(hào)。
(2)圖中的N個(gè)頂點(diǎn)依次存儲(chǔ)在頂點(diǎn)數(shù)組的[0]..[N-1]分
量中,稱0..N-1為各頂點(diǎn)的存儲(chǔ)序號(hào),簡(jiǎn)稱為頂點(diǎn)0,頂點(diǎn)
N-lo如不加說(shuō)明,在其它的存儲(chǔ)方法中也是如此。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義15
5、建立一個(gè)有向圖鄰接矩陣存儲(chǔ)的算法
【算法6-1】建立一個(gè)有向圖的鄰接矩陣存儲(chǔ)
voidCreateMGraph(IVIGraph*G)
{/*建立有向圖G的鄰接矩陣存儲(chǔ),N,E是圖的頂點(diǎn)個(gè)數(shù)和邊的個(gè)數(shù),
■nti,j,k,w;
charch;/*設(shè)圖的頂點(diǎn)信息為字符型*/
for(i=O;i<N;i++)scanf("%c”,&(G->vexs[i]));
/*輸入頂點(diǎn)信息,建立頂點(diǎn)表*/
for(i=O;i<N;i++)
for(j=O;j<N;j++)
G->edges[i][j]=O;/*初始化鄰接矩陣,
for(k=O;k<E;k++)
G->edges[i][j]=1;
/*若為無(wú)向圖,還要建立(j捋邊,即:G->edges[j][i]=1;*/
ZU1Z-H-/7JZ1口-II*7I/Xr10
22鄰接表
以
1、鄰接表的存儲(chǔ)思想
鄰接表(AdjacencyList)是圖的一種順序存儲(chǔ)與鏈?zhǔn)酱鎯?chǔ)結(jié)合
的存儲(chǔ)方法。鄰接表表示法類似于樹(shù)的孩子鏈表表示法。方法是
對(duì)于圖G中的每個(gè)頂點(diǎn)看,將所有鄰接于看的頂點(diǎn)Vj鏈成一個(gè)單鏈
表,這個(gè)單鏈表就稱為頂點(diǎn)看的鄰接表,再將所有點(diǎn)的鄰接表表
頭放到數(shù)組中,就構(gòu)成了圖的鄰接表。
下圖給出無(wú)向圖及對(duì)應(yīng)的鄰接表表示。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義17
4
序號(hào)vertexfiistedge
翱鄰糜表示
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義18
2、鄰接表的兩種結(jié)點(diǎn)結(jié)構(gòu)
頂點(diǎn)城朦甜旨針鄰接點(diǎn)域指針城
vertexfirstedgeadjvexnel
頂點(diǎn)表邊表
鄰接矩陣標(biāo)的結(jié)點(diǎn)結(jié)構(gòu)
頂點(diǎn)表的結(jié)點(diǎn)結(jié)構(gòu):由頂點(diǎn)域(vertex)和指向第一條鄰接
邊的指針域(firstedge)構(gòu)成。
邊表(即鄰接表)結(jié)點(diǎn)結(jié)構(gòu):由鄰接點(diǎn)域(adjvex)和指向下
一條鄰接邊的指針域(圖的next)構(gòu)成。對(duì)于網(wǎng)邊表需再增設(shè)一個(gè)
存儲(chǔ)邊上信息(如權(quán)值等)的域(inf。),網(wǎng)圖的邊表結(jié)構(gòu)如下
圖所示。鄰接點(diǎn)域邊上信息指針域
adjvexinfonext
網(wǎng)圖的邊超構(gòu)
2012年7月21日雙循循忸口乂19
J
3、鄰接表的形式描述
typedefstructnode
{intadjvex;/*鄰接點(diǎn)域*/
structnode*next;/*指向下一個(gè)鄰接點(diǎn)(或邊)的指針域*/
,一/*若要表示邊上信息,則應(yīng)增加相關(guān)數(shù)據(jù)域info*/
}EdgeNode;/*邊結(jié)點(diǎn)*/
typedefstructvnode
{VertexTypevertex;/*頂點(diǎn)域*/
EdgeNode*firstedge;/*第一條邊的指針*/
}VertexNode;/*頂點(diǎn)結(jié)點(diǎn)*/
VertexNodeAdjList[N];/*頂點(diǎn)結(jié)點(diǎn)向量*/
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義20
4、建立一^個(gè)有向圖鄰接表的算法
【算法6-2】建立一個(gè)有向圖的鄰接表存儲(chǔ)
voidCreateALGraph(VertexNodeAdjList[])
{/*建立有向圖的鄰接表存儲(chǔ),N,E是圖的頂點(diǎn)個(gè)數(shù)和邊的個(gè)數(shù)*/
inti,j,k;
EdgeNode*s;
for(i=0;i<N;i++)/*建立有n個(gè)頂點(diǎn)的頂點(diǎn)表*/
{scanf("%c",&(AdjList[i].vertex));/*讀入頂點(diǎn)信息*/
AdjList[i].firstedge=NULL;/*頂點(diǎn)的邊表頭指針設(shè)為空*/
)
for(k=0;k<E;k++)/*建立邊表*/
/*讀入邊的頂點(diǎn)序號(hào)對(duì)偶*/
{scanfC%d,%d",&i9&j);
s=(EdgeNode*)maHoc(siNeof(Ed9eNocle));/*新邊表結(jié)點(diǎn)s*/
s->adjvex=j;/*鄰接點(diǎn)序號(hào)為j*/
s->next=AdjList[i].firstedge;
/*將新邊表結(jié)點(diǎn)s插入到頂點(diǎn)vi的邊表頭部*/
AdjList[i].firstedge=s;
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義21
在建立鄰接表或逆鄰接表時(shí),若輸入的頂點(diǎn)信息即為頂點(diǎn)
的編號(hào),則建立鄰接表的復(fù)雜度為O(n+e),否則,需要通過(guò)
查找才能得到頂點(diǎn)在圖中位置,則時(shí)間復(fù)雜度為O(n-e)o
在鄰接表上容易找到任一頂點(diǎn)的第一個(gè)鄰接點(diǎn)和下一個(gè)鄰
接點(diǎn),但要判定任意兩個(gè)頂點(diǎn)(%和V,之間是否有邊或弧相連
,則需搜索第i個(gè)或第j個(gè)鏈表,因此,不及鄰接矩陣方便。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義22
5、鄰接表存儲(chǔ)方法的特點(diǎn)
(1)若無(wú)向圖中有n個(gè)頂點(diǎn)、c條邊,則它的鄰接表需n個(gè)頭結(jié)
點(diǎn)和2c個(gè)表結(jié)點(diǎn)。顯然,在邊稀疏(eV<n(n-1)/2)的情況下,用鄰
接表表示圖比鄰接矩陣節(jié)省存儲(chǔ)空間,當(dāng)和邊相關(guān)的信息較多時(shí)
更是如此。
(2)在無(wú)向圖的鄰接表中,頂點(diǎn)看的度恰為第i個(gè)鏈表中的結(jié)點(diǎn)
數(shù);而在有向圖中,第i個(gè)鏈表中的結(jié)點(diǎn)個(gè)數(shù)只是頂點(diǎn)看的出度,
為求人度,必須遍歷整個(gè)鄰接表。在所有鏈表中其鄰接點(diǎn)域的值
為i的結(jié)點(diǎn)的個(gè)數(shù)是頂點(diǎn)Vj的入度。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義23
6、有向圖的逆鄰接表一
若鄰接表的邊結(jié)點(diǎn)鏈表建立的是以治為頭的弧鏈表,這樣
的鄰接表稱為逆鄰接表。逆鄰接表便于確定頂點(diǎn)的入度或以
頂點(diǎn)X為頭的弧。
下圖所示為有向圖G2的鄰接表和逆鄰接表。
(a)W(b)逆避表
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義24
品畫的遍歷
圖的遍歷是指從圖中的任一頂點(diǎn)出發(fā),對(duì)圖中的所有頂點(diǎn)
訪問(wèn)一次且只訪問(wèn)一次。圖的遍歷是圖的一種基本操作,圖的
許多其它操作都是建立在遍歷操作的基礎(chǔ)之上。
由于圖結(jié)構(gòu)本身的復(fù)雜性,所以圖的遍歷操作也較復(fù)雜,
主要表現(xiàn)在以下四個(gè)方面:
①在圖結(jié)構(gòu)中,沒(méi)有一個(gè)“自然”的首結(jié)點(diǎn),圖中任意一
個(gè)頂點(diǎn)都可作為第一個(gè)被訪問(wèn)的結(jié)點(diǎn)。
②在非連通圖中,從一個(gè)頂點(diǎn)出發(fā),只能夠訪問(wèn)它所在的
連通分量上的所有頂點(diǎn),因此,還需考慮如何選取下一個(gè)出發(fā)
點(diǎn)以訪問(wèn)圖中其余的連通分量。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義25
③在圖結(jié)構(gòu)中,如果有回路存在,那么一個(gè)頂點(diǎn)被訪問(wèn)之后
,有可能沿回路又回到該頂點(diǎn)。
④在圖結(jié)構(gòu)中,一個(gè)頂點(diǎn)可以和其它多個(gè)頂點(diǎn)相連,當(dāng)這樣
的頂點(diǎn)訪問(wèn)過(guò)后,存在如何選取下一個(gè)要訪問(wèn)的頂點(diǎn)的問(wèn)題。
兩種遍歷方法:深度優(yōu)先搜索、廣度優(yōu)先搜索
3.1隆盛優(yōu)法搜索
深度優(yōu)先搜索(Depth_FisrstSearch)遍歷類似于樹(shù)的先根遍
歷,是樹(shù)的先根遍歷的推廣。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義26
1、深度優(yōu)先搜索的概念
假設(shè)初始狀態(tài)是圖中所有頂點(diǎn)未曾被訪問(wèn),則深度優(yōu)先搜
索可從圖中某個(gè)頂點(diǎn)發(fā)V出發(fā),訪問(wèn)此頂點(diǎn),然后依次從V的未被
訪問(wèn)的鄰接點(diǎn)出發(fā)深度優(yōu)先遍歷圖,直至圖中所有和V有路徑相
通的頂點(diǎn)都被訪問(wèn)到;若此時(shí)圖中尚有頂點(diǎn)未被訪問(wèn),則另選
圖中一個(gè)未曾被訪問(wèn)的頂點(diǎn)作起始點(diǎn),重復(fù)上述過(guò)程,直至圖
中所有頂點(diǎn)都被訪問(wèn)到為止。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義27
以下圖的無(wú)向圖G5為例,進(jìn)行圖的深度優(yōu)先搜索。必
假設(shè)從頂點(diǎn)%出發(fā)進(jìn)行搜索,在訪問(wèn)了頂點(diǎn)%之后,選擇鄰
接點(diǎn)V2。因?yàn)檠?未曾訪問(wèn),則從V2出發(fā)進(jìn)行搜索。依次類推,接著
從V4、Vg、V5出發(fā)進(jìn)行搜索。在訪問(wèn)了V5之后,由于V5的鄰接點(diǎn)
都已被訪問(wèn),則搜索回到V8o由于同樣的理由,搜索繼續(xù)回到V4
,V2直至V[,此時(shí)由于當(dāng)?shù)牧硪粋€(gè)鄰接點(diǎn)未被訪問(wèn),則搜索又從V1
到V3,再繼續(xù)進(jìn)行下去由此,得到的頂點(diǎn)訪問(wèn)序列為:
2012年7月21日28
2、圖的深度優(yōu)先遍歷算法;
-在遍歷過(guò)程中必須能夠區(qū)分頂點(diǎn)是否已被訪問(wèn)「因此需附設(shè)一
訪問(wèn)標(biāo)志數(shù)組flag[N],用flag[O]..flag[N-l]來(lái)標(biāo)示相應(yīng)的頂點(diǎn)是否
訪問(wèn)過(guò),其初值為0,一旦某個(gè)頂點(diǎn)被訪問(wèn),則其相應(yīng)的分量置
為1。
(1)形式算法
【算法6-4]圖的深度優(yōu)先遍歷
intflag[N]={0};/*N為圖的頂點(diǎn)個(gè)數(shù)*/
voidDFSTraverse(Graph*G,intv)
{Visited(v);flag[v]=1;/*訪問(wèn)頂點(diǎn)v,并置訪問(wèn)標(biāo)記*/
for(w=FisrAdjVex(G,v);w;w=NextAdjVex(G,v,w))
if(!flag[w])
DFSTraverse(G,w);
)
(2)以鄰接表為存儲(chǔ)結(jié)構(gòu)實(shí)現(xiàn)圖的深度優(yōu)先遍歷顯
【算法6?5】深度優(yōu)先遍歷鄰接表存儲(chǔ)的圖
intflag[N]={0};/*全局?jǐn)?shù)組初始化為0*/
voidDFS(VertexNodeAdjList[],inti)
{/*以頂點(diǎn)[為出發(fā)點(diǎn),對(duì)鄰接表存儲(chǔ)的圖G進(jìn)行DFS搜索*/
EdgeNode*p;
Visited(AdjList[i].vertex);/*訪問(wèn)頂點(diǎn)vi*/
flag[i]=1;/*標(biāo)記頂點(diǎn)i已訪問(wèn)*/
p=AdjList[i].firstedge;/*取頂點(diǎn)i鄰接邊鏈表的頭指針*/
while(p)
{j=p->adjvex;/*依次搜索頂點(diǎn)i的鄰接點(diǎn)頂點(diǎn)j*/
if(!flag[jj)/*若頂點(diǎn)j尚未訪問(wèn),則以頂點(diǎn)j為出發(fā)點(diǎn)深度搜索*/
DFS(AdjList,j);
p=p->next;/*找頂點(diǎn)i的下一個(gè)鄰接點(diǎn)*/
}
)
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義30
voidDFSTraverseAL(VertexNodeAdjList[])
inti;
for(i=0;i<N;i++)
if(!flag[i])
DFS(AdjList,i);
3、算法分析
如果圖是連通的,函數(shù)DFS只需被外界函數(shù)調(diào)用一次,
圖中的各個(gè)頂點(diǎn)就全部得到訪問(wèn)。如果圖是非連通的,函
數(shù)DFS被外界函數(shù)調(diào)用一次僅訪問(wèn)了包括出發(fā)點(diǎn)的連通分量
,要想訪問(wèn)其它連通分量,必須找另一個(gè)連通分量上的頂
點(diǎn)作出發(fā)點(diǎn),有幾個(gè)連通分量就要調(diào)用幾次DFS才能訪問(wèn)全
圖,因此需要函數(shù)DFSTraverseAL。雖然對(duì)DFS的調(diào)用出現(xiàn)
在循環(huán)中,對(duì)每個(gè)頂點(diǎn)都可以調(diào)用一次DFS函數(shù),但一旦某
個(gè)頂點(diǎn)被標(biāo)志成已訪問(wèn)標(biāo)志,就不再?gòu)乃霭l(fā)進(jìn)行搜索,
所以實(shí)質(zhì)上是圖中有幾個(gè)連通分量,通過(guò)DFSTraverseAL就
會(huì)幾次調(diào)用DFS函數(shù)。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義32
在遍歷時(shí),對(duì)圖中每個(gè)頂點(diǎn)至多調(diào)用一次DFS函數(shù),因?yàn)?/p>
一旦某個(gè)頂點(diǎn)被標(biāo)志成已被訪問(wèn),就不再?gòu)乃霭l(fā)進(jìn)行搜索。
因此,遍歷圖的過(guò)程實(shí)質(zhì)上是對(duì)每個(gè)頂點(diǎn)查找其鄰接點(diǎn)的過(guò)程
o其耗費(fèi)的時(shí)間則取決于所采用的存儲(chǔ)結(jié)構(gòu)。當(dāng)用二維數(shù)組表
示鄰接矩陣圖的存儲(chǔ)結(jié)構(gòu)時(shí),查找每個(gè)頂點(diǎn)的鄰接點(diǎn)所需時(shí)間
為og2),其中n為圖中頂點(diǎn)數(shù)。而當(dāng)以鄰接表作圖的存儲(chǔ)結(jié)構(gòu)時(shí)
,找鄰接點(diǎn)所需時(shí)間為。⑥,其中e為無(wú)向圖中邊的數(shù)或有向圖
中弧的數(shù)。由此,當(dāng)以鄰接表作存儲(chǔ)結(jié)構(gòu)時(shí),深度優(yōu)先搜索遍
歷圖的時(shí)間復(fù)雜度為O(n+e)o
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義33
52廣度優(yōu)法搜索
廣度優(yōu)先搜索(Brcadth_FirstSearch)遍歷類似于樹(shù)的按層次
遍歷的過(guò)程。
1、廣度優(yōu)先搜索的概念
假設(shè)從圖中某頂點(diǎn)v出發(fā),在訪問(wèn)了v之后依次訪問(wèn)v的各個(gè)未
曾訪問(wèn)過(guò)和鄰接點(diǎn),然后分別從這些鄰接點(diǎn)出發(fā)依次訪問(wèn)它們的
鄰接點(diǎn),并使“先被訪問(wèn)的頂點(diǎn)的鄰接點(diǎn)”先于“后被訪問(wèn)的頂
點(diǎn)的鄰接點(diǎn)”被訪問(wèn),直至圖中所有已被訪問(wèn)的頂點(diǎn)的鄰接點(diǎn)都
被訪問(wèn)到。若此時(shí)圖中尚有頂點(diǎn)未被訪問(wèn),則另選圖中一個(gè)未曾
被訪問(wèn)的頂點(diǎn)作起始點(diǎn),重復(fù)上述過(guò)程,直至圖中所有頂點(diǎn)都被
訪問(wèn)到為止。換句話說(shuō),廣度優(yōu)先搜索遍歷圖的過(guò)程中以v為起
始點(diǎn),由近至遠(yuǎn),依次訪問(wèn)和v有路徑相通且路徑長(zhǎng)度為1,2,…的
頂點(diǎn)。34
例如,對(duì)下圖所示無(wú)向圖G5進(jìn)行廣度優(yōu)先搜索遍歷,首先
訪問(wèn)V1和V1的鄰接點(diǎn)V2和丫3,然后依次訪問(wèn)V2的鄰接點(diǎn)V4和V5及
V3的鄰接點(diǎn)V6和V7,最后訪問(wèn)的鄰接點(diǎn)Vg。由于這些頂點(diǎn)的鄰
接點(diǎn)均已被訪問(wèn),并且圖中所有頂點(diǎn)都被訪問(wèn),由些完成了圖
的遍歷。得到的頂點(diǎn)訪問(wèn)序列為:
2012年7月21日姒站笫惚護(hù)乂35
2、圖的廣度優(yōu)先遍歷算法
和深度優(yōu)先搜索類似,在遍歷的過(guò)程中也需要一個(gè)訪問(wèn)標(biāo)志
數(shù)組。并且,為了順次訪問(wèn)路徑長(zhǎng)度為2、3、…的頂點(diǎn),需附設(shè)
隊(duì)列以存儲(chǔ)已被訪問(wèn)的路徑長(zhǎng)度為1、2、…的頂點(diǎn)。
【算法6-6】圖的廣度優(yōu)先遍歷
intflag[N]={0};/*全局?jǐn)?shù)組初始化為0*/
voidBFSTraverse(Graph*G,intv)
{/*對(duì)G進(jìn)行廣度優(yōu)先遍歷*/
InitQueue(Q);/*置空的隊(duì)列Q*/
if(!flag[v])/*v尚未訪問(wèn)*/
{EnQueue(Q,v);/*v入隊(duì)*/
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義36
3
while(IQueueEmpty(Q))/*隊(duì)列不空*/
{DeQueue(Q,u);/*隊(duì)頭元素出隊(duì)*/
Visited(u);/*訪問(wèn)該頂點(diǎn)*/
flag[u]=l;/*置訪問(wèn)標(biāo)志*/
for(w=FirstAdjVex(G,u);w;w=NextAdjVex(G,u,w))
if(!flag[w])/*依次將尚未訪問(wèn)的鄰接頂點(diǎn)*/
EnQueue(Q,w);
(2)以鄰接矩陣為存儲(chǔ)結(jié)構(gòu)實(shí)現(xiàn)廣度優(yōu)先遍歷
【算法6?7】廣度優(yōu)先遍歷鄰接矩陣存儲(chǔ)的圖
intflag[N]={0};/*全局?jǐn)?shù)組初始化為0*/
voidBFS(MGraph*G,inti)
{/*以頂點(diǎn)i為出發(fā)點(diǎn),對(duì)鄰接矩陣存儲(chǔ)的圖G進(jìn)行BFS搜索*/
■ntj;
intQ[N],front,rear;/*定義隊(duì)列空間和隊(duì)頭隊(duì)尾變量*/
front=0;rear=-1;/*初始化為空,
Visited(G->vexs[i]);/*訪問(wèn)頂點(diǎn)產(chǎn)/
flag[i]=1;/*置訪問(wèn)標(biāo)志*/
rear++;Q[rear]=i;/*出發(fā)點(diǎn)頂點(diǎn)i入隊(duì),
while(front<=rear)/*當(dāng)隊(duì)不空*/
{i=Q[rear];front++;/*出隊(duì)*/
for0=0;j<N;j++)/*依次搜索頂點(diǎn)[的鄰接點(diǎn)*/
if(G->edges[i][j]==1&&!flag[jj)/*若鄰接點(diǎn)頂點(diǎn)j未訪問(wèn),
{Visited(G->vexs[j]);/*訪問(wèn)頂點(diǎn)j*/
flag[j]=1;/*置訪問(wèn)標(biāo)志*/
rear++;Q[rear]=j;/*訪問(wèn)過(guò)的頂點(diǎn)j入隊(duì)*/
voidBFSTraverseAL(Mgraph*G)
inti;
for(i=0;i<N;i++)
if(!flag[i])BFS(G,i);
3、算法分析
同樣,對(duì)于一個(gè)連通圖一次調(diào)用BFS就能訪問(wèn)所有的頂點(diǎn),
對(duì)于非連通圖只能遍歷包括出發(fā)點(diǎn)的連通分量,如遍歷其它的
連通分量,需再選擇其它連通分量上的頂點(diǎn)做出發(fā)點(diǎn)。
分析上述算法可知,每個(gè)頂點(diǎn)至多進(jìn)一次隊(duì)列。遍歷圖的
過(guò)程實(shí)質(zhì)是通過(guò)邊或弧找鄰接點(diǎn)的過(guò)程,因此廣度優(yōu)先搜索遍
歷圖的時(shí)間復(fù)雜度和深度優(yōu)先搜索遍歷相同,兩者不同之處僅
僅在于對(duì)頂點(diǎn)訪問(wèn)的順序不同。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義40
M3應(yīng)用囹的遍歷囹判斷囹的接通但
1.無(wú)向圖的連通性
在對(duì)無(wú)向圖進(jìn)行遍歷時(shí),對(duì)于連通圖,僅需從圖中任一頂點(diǎn)
出發(fā),進(jìn)行深度優(yōu)先搜索或廣度優(yōu)先搜索,便可訪問(wèn)到圖中所
有頂點(diǎn)。對(duì)非連通圖,則需從多個(gè)頂點(diǎn)出發(fā)進(jìn)行搜索,而每一
次從一個(gè)新的起始點(diǎn)出發(fā)進(jìn)行搜索過(guò)程中得到的頂點(diǎn)訪問(wèn)序列
恰為其各個(gè)連通分量中的頂點(diǎn)集。
非連通圖G3:按照G3的鄰接表進(jìn)行深度優(yōu)先搜索遍歷,需由
算法調(diào)用兩次DFS(即分別從頂點(diǎn)A和D出發(fā)),得到的頂點(diǎn)訪
問(wèn)序列分別為:
ABFEDC
這兩個(gè)頂點(diǎn)集分別加上所有依附于這些頂點(diǎn)的邊,便構(gòu)
成了非連通圖G3的兩個(gè)連通分量。41
序號(hào)
A
014A
1B05A
2C3A
D
32A
4E
05A
F
514A
(a)無(wú)向圖G3
G3的球表
因此,要想判定一個(gè)無(wú)向圖是否
為連通圖,或有幾個(gè)連通分量,就可
設(shè)一個(gè)計(jì)數(shù)變量count,初始時(shí)取值為0,
在算法6-5的第二個(gè)for循環(huán)中,每調(diào)用
一次DFS,就給count增1。這樣,當(dāng)整
(b)G3的兩徜1通分量
個(gè)算法結(jié)束時(shí),依據(jù)count的值,就可
確定圖的連通性了。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義42
2.有向圖的連通性
有向圖的連通性不同于無(wú)向圖的連通性,可分為弱連通、
單側(cè)連通和強(qiáng)連通。對(duì)有向圖的強(qiáng)連通性以及強(qiáng)連通分量的判
定,可通過(guò)對(duì)以十字鏈表為存儲(chǔ)結(jié)構(gòu)的有向圖的深度優(yōu)先搜索
實(shí)現(xiàn)。
由于強(qiáng)連通分量中的結(jié)點(diǎn)相互可達(dá),故可先按出度深度優(yōu)
先搜索,記錄下訪問(wèn)結(jié)點(diǎn)的順序和連通子集的劃分,再按入度
深度優(yōu)先搜索,對(duì)前一步的結(jié)果再劃分,最終得到各強(qiáng)連通分
量。若所有結(jié)點(diǎn)在同一個(gè)強(qiáng)連通分量中,則該圖為強(qiáng)連通圖。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義43
4、女感樹(shù)我景小皮戚樹(shù)
41景小女感樹(shù)
1、最小生成樹(shù)的概念
由生成樹(shù)的定義可知,無(wú)向連通圖的生成樹(shù)不是唯一的。連
通圖的一次遍歷所經(jīng)過(guò)的邊的集合及圖中所有頂點(diǎn)的集合就構(gòu)
成了該圖的一棵生成樹(shù),對(duì)連通圖的不同遍歷,如遍歷出發(fā)點(diǎn)
不同或存儲(chǔ)點(diǎn)的順序不同,就可能得到不同的生成樹(shù)。下圖(a)
、(b)和?所示的均為無(wú)向連通圖G5的生成樹(shù)。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義44
⑴對(duì)于有n個(gè)頂點(diǎn)的無(wú)向連通圖,無(wú)論其生成樹(shù)的形態(tài)如何
,所有生成樹(shù)中都有且僅有n—1條邊。
⑵如果無(wú)向連通圖是一個(gè)網(wǎng),那么,它的所有生成樹(shù)中必
有一棵邊的權(quán)值總和最小的生成樹(shù),我們稱這棵生成樹(shù)為最小
生成樹(shù),簡(jiǎn)稱為最小生成樹(shù)。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義45
2、如何找到一個(gè)連通網(wǎng)絡(luò)的最小生成樹(shù)?5
(1)MST,性質(zhì):
MST性質(zhì):設(shè)G=(Vn,En)是一個(gè)連通網(wǎng)絡(luò),U是頂點(diǎn)集Vn
的一個(gè)真子集。若⑴,v)是G中所有的一個(gè)端點(diǎn)在U(即uCU)
而另一個(gè)端點(diǎn)不在U(即vGVn—U)里的邊中,具有最小權(quán)值
的一條邊,則一定存在的一棵最小生成樹(shù)包括此邊
G(u,v)o
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義46
MST性質(zhì)的用反證法證明:---—一
即首先假設(shè)G的任何一棵最小生成樹(shù)中都不含此邊(u,v),
設(shè)T是G的一棵最小生成樹(shù),但不包含邊(u,v)。由于T是樹(shù)且是
連通的,因此有一條從u到v的路徑;且該路徑上必有一條連接
兩頂點(diǎn)集U和Vn—U的邊(u',v'),其中u'WU,v'€Vn-U
,否則u和v不連通。當(dāng)把邊(u,v)加入樹(shù)T時(shí),得到一^個(gè)含有邊
(U,V)的回路。若刪去邊(U‘,V’),則上述回路即被消除,由此
得到另一棵生成樹(shù)T',T’和T的區(qū)別僅在于用邊(u,V)取代了
T中的邊(u‘,v’)。因?yàn)?u,v)的權(quán)W(u',v')的權(quán),故T'的
權(quán)WT的權(quán),因此T'也是G的最小生成樹(shù),它包含邊(u,v),與
假設(shè)矛盾。MST性質(zhì)得以證明。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義47
42構(gòu)造景小金鼠樹(shù)的儂勿喜法
1、Prim算法
設(shè)G=(Vn,E,為一網(wǎng)圖,其中V。為網(wǎng)圖中所有頂點(diǎn)的集合
,En為網(wǎng)圖中所有帶權(quán)邊的集合。
設(shè)置兩個(gè)新的集合U和T,其中集合U用于存放G的最小生
成樹(shù)中的頂點(diǎn),集合T存放G的最小生成樹(shù)中的邊。令集合U的
初值為U={u。}(設(shè)從頂點(diǎn)u0出發(fā)構(gòu)造最小生成樹(shù)),集合T的
初值為T={}。Prim算法的思想是,從所有uWU,vGV”一U的
邊中,選取具有最小權(quán)值的邊(u,v),將頂點(diǎn)v加入集合U中,將
邊(u,V)加入集合T中,如此不斷重復(fù),直到U=Vn時(shí),最小生成
樹(shù)構(gòu)造完畢,這時(shí)集合T中包含了最小生成樹(shù)的所有邊。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義48
Prim算法可用下述過(guò)程描述,其中用W.表示頂點(diǎn)u與頂點(diǎn)v
邊上的權(quán)值。
(l)U={u0}?T={};
(2)while(U^VJdo
.(u,v)=min{wuv|u€U,v€Vn-U)
T=T+{(u,v)}
U=U+{v}
⑶結(jié)束。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義49
2、Prim過(guò)程
下圖(a)所示的一個(gè)網(wǎng)圖,按照Prim方法,從頂點(diǎn)1出發(fā),該網(wǎng)
的最小生成樹(shù)的產(chǎn)生過(guò)程如圖(b)、(c)、(d)、⑹、⑴和(g)所示。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義50
3、Prim算法實(shí)現(xiàn):
這里設(shè)置三個(gè)輔助向量cost[N]、tree[N]>flag[N]:
其中cost用來(lái)保存屬于集合U中的頂點(diǎn)連通不屬于集合U中
的每一頂點(diǎn)的邊中具有最小值邊的權(quán)值,cost的最終值是最小生
成樹(shù)中每條邊的權(quán)值;
數(shù)組tree對(duì)應(yīng)cost,用來(lái)保存依附于該邊的在集合U中的頂點(diǎn)
,如tree[4]=l,說(shuō)明當(dāng)前這條邊是(1,4),即用頂點(diǎn)1連通的頂點(diǎn)4
,其權(quán)值保存在cost[4]中;flag仍為標(biāo)志數(shù)組,用來(lái)標(biāo)明某一點(diǎn)
是否進(jìn)入了U。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義51
表6-1給出了用上述算法構(gòu)造網(wǎng)圖6-22⑷的最小生成樹(shù)的過(guò)
程中,數(shù)組tree、cost以及集合U的變化情況,
表6」用Prim算法構(gòu)造最小生成樹(shù)過(guò)程中各參數(shù)的變化示意
Q)
(2)⑶(4)(6)(7)
頂點(diǎn)(初始狀態(tài))
costtreecosttreecosttreecosttreecosttreecosttreecosttree
000000000000000
1500國(guó)o國(guó)o國(guó)o國(guó)0國(guó)0回o
2600600600523523456網(wǎng)6
38(J651504國(guó)4國(guó)4國(guó)404
01£11
480401畫1圓1圓1
8Q8(J
570430303回3國(guó)3
03
68(J8(J80423423畫3
{0}{0,1}{0J,4}{0,1,4,3){0,143,5}{0"{0,1,43
U
3,5,6}5,6,2}
(){(0,1)}{(0」),?1),(1⑼{。1),(L4),{(0,1),(1,4),?1),。,4),
T。倒(43}(4,3)3)}(4,3),(3,5),(4,3),(3,5),
0,6)}(3,6),(6,2))
【算法6-9]用Prim算法構(gòu)造無(wú)向連通網(wǎng)的最小生成樹(shù)
#defineMAXCOSTj■/*定義MAXCOST為一個(gè)足夠大的常量值*/
voidPrim(intgm[N][N],inttree[N],intcost[N])
{/*從序號(hào)為。的頂點(diǎn)出發(fā),建立最小生成樹(shù),9m[N][N]是其鄰接矩陣*/
/*建立的最小生成樹(shù)存于數(shù)組tree中,對(duì)應(yīng)的邊值在cost中*/
intflag[N]={0};
inti,j,k,mincost;
for(i=O;i<N;i++)
/*從存儲(chǔ)序號(hào)為。的頂點(diǎn)出發(fā)生成最小生成樹(shù)*/
tree[i]=O;
}
flag[0]=1;
for(i=1;i<N;i++)/*N一次循環(huán),尋找當(dāng)前最小權(quán)值的邊,
{mincost=MAXCOST;
fora=1;j<N;j++)
{if(flag[j]==0&&cost[j]<mincost)
{mincost=cost[j];
k=j;
/*記憶最小的邊*/
flag[k]=l;
for(j=l;j<N;j++)
if(gm[k][j]<cost[j])
{cost[j]=gm[k][j];
tree[j]=k;
4、時(shí)間性能
在Prim算法中,第一個(gè)for循環(huán)的執(zhí)行次數(shù)為n—1,第二個(gè)
for循環(huán)中又包括了一個(gè)while循環(huán)和一個(gè)for循環(huán),執(zhí)行次數(shù)為
2(n-l)2,所以Prim算法的時(shí)間復(fù)雜度為:O(n2)
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義55
44構(gòu)造景小金鼠樹(shù)的加等讓
Kruskal算法是一種按照網(wǎng)中邊的權(quán)值遞增的順序構(gòu)造最小生成
樹(shù)的方法。
1、Kruskal算法基本思想
設(shè)無(wú)向連通網(wǎng)為G=(Vn,En),令G的最小生成樹(shù)為T=(V『ET)
,其初態(tài)為:V=V即開(kāi)始時(shí)頂點(diǎn)集T為V0,邊集T
Tn,ET={},E
為空,此時(shí)T中沒(méi)有邊,即各頂點(diǎn)各自構(gòu)成一個(gè)連通子圖。然后
從沒(méi)有進(jìn)入ET的邊集(E「-ET)中不斷選取權(quán)值最小的邊,若該
邊的兩個(gè)頂點(diǎn)屬于T的兩個(gè)不同的連通子圖,加入該邊不構(gòu)成回
路,則將此邊作為最小生成樹(shù)的邊加入到ET中;若該邊的加入
造成回路,則舍去此邊,則選取下一條權(quán)值較小的邊,如此下
去,選取n-l次后,此時(shí)ET中必有n-l條邊,n-l條邊連通了n個(gè)頂
點(diǎn),連通子圖的個(gè)數(shù)為1,此連通子圖便為G的一棵最小生成樹(shù)
O
2、Kruskal方法過(guò)程
對(duì)于下圖所示的網(wǎng),按照Kruskal方法構(gòu)造最小生成樹(shù)的過(guò)程
如下圖所示。在構(gòu)造過(guò)程中,按照網(wǎng)中邊的權(quán)值由小到大的順
序,不斷選取當(dāng)前未被選取的邊集中權(quán)值最小的邊。依據(jù)生成
樹(shù)的概念,n個(gè)結(jié)點(diǎn)的生成樹(shù),有n—1條邊,故反復(fù)上述過(guò)程,
直到選取了n—1條邊為止,就構(gòu)成了一棵最小生成樹(shù)。
3、Kruskal算法的實(shí)現(xiàn)
⑴相關(guān)的數(shù)據(jù)結(jié)構(gòu),邊的表示如下:
typedefstruct
{intVp
;是兩個(gè)頂點(diǎn)的序號(hào)*/
intv2/*vPV2
intcost;/*邊的權(quán)值*/
}EdgeType;
EdgeTypeedges[E],T[N-1];
向量edges存儲(chǔ)網(wǎng)中所有的邊,每個(gè)分量cdges[i]代表網(wǎng)中的一
條邊,其中edges[i].V[和edges[i]凡表示該邊的兩個(gè)頂點(diǎn)的序號(hào)
(0..N-1),edgcs[i].cost表示這條邊的權(quán)值;最終最小生成樹(shù)的邊
存放在
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義58
在結(jié)構(gòu)數(shù)組edges中,每個(gè)分量edges[i]代表網(wǎng)中的一條邊,
其中edges[i].v[和edges[I]上表示該邊的兩個(gè)頂點(diǎn),edges[i].cost表
示這條邊的權(quán)值。為了方便選取當(dāng)前權(quán)值最小的邊,事先把
數(shù)組edges中的各元素按照其cost域值由小到大的順序排列。
edges數(shù)組狀態(tài)如下:
/p>
v25466143235
cost30404245505052606570
數(shù)據(jù)結(jié)構(gòu)講義
2012年7月21日59
father數(shù)組,因?yàn)榭偸且_定兩個(gè)頂點(diǎn)是否屬于同一個(gè)集合(
一個(gè)連通子圖中包含的頂點(diǎn)認(rèn)為是一個(gè)集合),因此設(shè)計(jì)一個(gè)
數(shù)組:
intfather[N];
利用father]],可以通過(guò)回溯的方法最終確定頂點(diǎn)i所在的集
合(找到集合的根結(jié)點(diǎn),集合的表示及合并采用5.9.2節(jié)所介紹的
方法)。
初值:表示各個(gè)頂點(diǎn)在不同的集
father[i]=-l(i=O,l/--,N-l),
合上。
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義60
依次取出edges數(shù)組中沒(méi)有選入T中的最小邊的兩個(gè)頂點(diǎn),查
找它們所屬的集合,若不在一^個(gè)集合中就選中這條邊,即把這
條邊加入到T中,因此連通了兩個(gè)集合。
兩個(gè)變量:intvfi,vf2;存儲(chǔ)兩頂點(diǎn)所在集合的根結(jié)點(diǎn)若不
等于vf2,表明這條邊的兩個(gè)頂點(diǎn)不屬于同一集合,則將這條邊
作為最小生成樹(shù)的邊選入到T中,并合并它們所屬的兩個(gè)集合。
father數(shù)組的變化情況如表6-2所示。
father[]0123456加入的邊對(duì)應(yīng)的頂點(diǎn)集合
-1■4-4-4-■4-4-1
-1-1-1-1-13-1(3,5)(3,5)
-1-1-1-113-1(1,4)(3,5),(1,4)
-1-1-1-1133(3,6)(3,5,6),(1,4)
-1-1-12133(2,6)(3,5,6,2),(1,4)
-10-12133(0,1)(3,5,6,2),(1,4,0)
20-12133(3,4)(3,5,6,2,1,4,0)
(3)算法實(shí)現(xiàn)____
[算法0]Kruskal方法構(gòu)造無(wú)向網(wǎng)的最小生成樹(shù)
voidKruskal(EdgeTypeedges[],EdgeTypeT[])
{/*用Kruskal方法構(gòu)造圖的最小生成樹(shù)*/
中是圖中各條邊,且已按其權(quán)值從小到大有序,最小生成樹(shù)的邊在T中,
intfather[N];
inti,j,vf1,vf2;
for(i=O;i<N;i++)father[i]=-1;
i=O;j=O;
while(i<E&&j<N-1)
{vf1=Find(father,edges[i].v1);
vf2=Find(father,edges[i].v2);
if(vf1!=vf2)
{father[vf2]=vf1;
T[j]=edges[i];
j++;
■++;
2012年7月21日數(shù)據(jù)結(jié)構(gòu)講義62
intFind(intfather口,intv)
intt;
t=v;
while(father[t]>=0)
t=fatherft];
return(t);
___________________一一一―――14
在Kruskal算法中,while循環(huán)是影響時(shí)間效率的主要操作,其
循環(huán)次數(shù)最多為e次,其內(nèi)部調(diào)用的Find函數(shù)的內(nèi)部循環(huán)次數(shù)最
多為n次,所以Kruskal算
溫馨提示
- 1. 本站所有資源如無(wú)特殊說(shuō)明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁(yè)內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒(méi)有圖紙預(yù)覽就沒(méi)有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫(kù)網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。
最新文檔
- 語(yǔ)文課外閱讀與語(yǔ)文成績(jī)提升的關(guān)聯(lián)性
- 家庭書房裝飾設(shè)計(jì)與文化品味塑造
- 現(xiàn)代化辦公室中的高效媒體設(shè)備和軟件投資規(guī)劃
- 2025年度項(xiàng)目負(fù)責(zé)人聘用合同(智慧農(nóng)業(yè)項(xiàng)目負(fù)責(zé)人)
- 2025年度清雪承包合同-城市橋梁積雪清除與安全檢查
- 現(xiàn)代化小學(xué)課堂的硬件設(shè)備選型與應(yīng)用策略
- 2025年度測(cè)繪公司內(nèi)部保密協(xié)議及競(jìng)業(yè)禁止合同
- 疫情背景下的線上心理健康教育研究報(bào)告
- 二零二五年度城市景觀照明設(shè)計(jì)合同正式版
- 2025年度房地產(chǎn)銷售項(xiàng)目提成合同
- 中央2025年公安部部分直屬事業(yè)單位招聘84人筆試歷年參考題庫(kù)附帶答案詳解
- 三年級(jí)數(shù)學(xué)(上)計(jì)算題專項(xiàng)練習(xí)附答案
- 中醫(yī)診療方案腎病科
- 2025年安慶港華燃?xì)庀薰菊衅腹ぷ魅藛T14人高頻重點(diǎn)提升(共500題)附帶答案詳解
- 人教版(2025新版)七年級(jí)下冊(cè)數(shù)學(xué)第七章 相交線與平行線 單元測(cè)試卷(含答案)
- 2025年供電所所長(zhǎng)個(gè)人工作總結(jié)(2篇)
- 玩具有害物質(zhì)風(fēng)險(xiǎn)評(píng)估-洞察分析
- 春節(jié)節(jié)后復(fù)工全員安全意識(shí)提升及安全知識(shí)培訓(xùn)
- 2024年3月天津第一次高考英語(yǔ)試卷真題答案解析(精校打?。?/a>
- 2024年河南省公務(wù)員錄用考試《行測(cè)》真題及答案解析
- 2023年上海鐵路局集團(tuán)有限公司招聘筆試真題
評(píng)論
0/150
提交評(píng)論