有向圖的鄰接表格儲存體,遞迴和非遞迴的深度、廣度遍曆(codeblocks+gcc)

來源:互聯網
上載者:User
程式功能:

1. 圖的鄰接表格儲存體

2. 遞迴深度遍曆

3. 非遞迴深度遍曆(藉助stack)

4. 遞迴廣度遍曆

5. 非遞迴廣度遍曆(藉助queue)

 

程式中通過條件編譯實現,遞迴與非遞迴的選擇

//#define _RECURSION_TRAVERSE //遞迴遍曆(將下一行注釋,此行不注釋)<br />#define _NON_RECURSION_TRAVERSE //非遞迴遍曆(節點本身有isVisited域)(將上一行注釋,此行不注釋)

注釋第一行,保留第二行:實現非遞迴遍曆

注釋第二行,保留第一行:實現遞迴遍曆

兩行都注釋或都不注釋:出錯(無此函數/函數重名)

 

程式所用圖的結構

程式原始碼

/*****************************************************************<br /> *功 能:利用鄰接表格儲存體圖,實現其遞迴與非遞迴的深度遍曆和廣度遍曆<br /> *作 者:JarvisChu<br /> *時 間:2011-04-30<br /> *****************************************************************/<br />#include <iostream><br />#include <string><br />#include <stack><br />#include <queue></p><p>using namespace std;</p><p>//#define _RECURSION_TRAVERSE //遞迴遍曆(將下一行注釋,此行不注釋)<br />#define _NON_RECURSION_TRAVERSE //非遞迴遍曆(節點本身有isVisited域)(將上一行注釋,此行不注釋)</p><p>#define MAX_VERTEX_NUM 20 //最大頂點數</p><p>/*弧節點的結構,即每個頂點後面的單鏈表中的節點結構*/<br />typedef struct ArcNode{<br /> int adjvex; //該弧所指向的頂點的位置<br /> struct ArcNode* nextArc; //下一條弧<br /> string info; //該弧所攜帶的資訊<br />}ArcNode;</p><p>#ifdef _NON_RECURSION_TRAVERSE<br />/*每個頂點的節點結構,非遞迴時使用*/<br />typedef struct VNode{<br /> bool isVisited;<br /> string data; //頂點的資料<br /> ArcNode* fristArc; //指向該頂點所接的單鏈表的第一個弧節點<br />}VNode,AdjList[MAX_VERTEX_NUM];<br />#endif</p><p>#ifdef _RECURSION_TRAVERSE<br />/*每個頂點的節點結構,遞迴時使用*/<br />typedef struct VNode{<br /> string data; //頂點的資料<br /> ArcNode* fristArc; //指向該頂點所接的單鏈表的第一個弧節點<br />}VNode,AdjList[MAX_VERTEX_NUM];<br />#endif</p><p>/*圖的結構*/<br />typedef struct{<br /> AdjList vertices; //頂點數組<br /> int vexNum; //頂點數<br /> int arcNum; //弧數<br /> int kind; //種類<br />}Graph;</p><p>/*初始化有向圖*/<br />bool InitDiGraph(Graph* pGraph){<br /> pGraph->kind = 0; //有向圖<br /> pGraph->vexNum = 5;<br /> pGraph->arcNum = 5;</p><p> pGraph->vertices[0].data = "V0"; //頂點V0的鄰接表<br />#ifdef _NON_RECURSION_TRAVERSE<br /> pGraph->vertices[0].isVisited = false;<br />#endif<br /> ArcNode* node = new ArcNode();<br /> node->adjvex = 1;<br /> node->info = "V0-->V1";<br /> node->nextArc = NULL;<br /> ArcNode* node1 = new ArcNode();<br /> node1->adjvex = 2;<br /> node1->info = "V0-->V2";<br /> node1->nextArc = NULL;<br /> node->nextArc = node1;<br /> pGraph->vertices[0].fristArc = node;</p><p> pGraph->vertices[1].data = "V1"; //頂點V1的鄰接表<br /> #ifdef _NON_RECURSION_TRAVERSE<br /> pGraph->vertices[1].isVisited = false;<br /> #endif<br /> pGraph->vertices[1].fristArc = NULL;</p><p> pGraph->vertices[2].data = "V2"; //頂點V2的鄰接表<br />#ifdef _NON_RECURSION_TRAVERSE<br /> pGraph->vertices[2].isVisited = false;<br /> #endif<br /> node = new ArcNode();<br /> node->adjvex = 3;<br /> node->info = "V2-->V3";<br /> node->nextArc = NULL;<br /> pGraph->vertices[2].fristArc = node;</p><p> pGraph->vertices[3].data = "V3"; //頂點V3的鄰接表<br /> #ifdef _NON_RECURSION_TRAVERSE<br /> pGraph->vertices[3].isVisited = false;<br /> #endif<br /> node = new ArcNode();<br /> node->adjvex = 0;<br /> node->info = "V3-->V0";<br /> node->nextArc = NULL;<br /> node1 = new ArcNode();<br /> node1->adjvex = 4;<br /> node1->info = "V3-->V4";<br /> node1->nextArc = NULL;<br /> node->nextArc = node1;<br /> pGraph->vertices[3].fristArc = node;</p><p> pGraph->vertices[4].data = "V4"; //頂點V4的鄰接表<br /> #ifdef _NON_RECURSION_TRAVERSE<br /> pGraph->vertices[4].isVisited = false;<br /> #endif<br /> pGraph->vertices[4].fristArc = NULL;</p><p> return true;<br />}</p><p>/*顯示有向圖*/<br />bool DisplayDiGraph(Graph diGraph){<br /> cout<<"*******************圖資訊********************"<<endl;<br /> cout<<"圖種類為:"<<diGraph.kind<<endl;<br /> cout<<"頂點數為:"<<diGraph.vexNum<<endl;<br /> cout<<"弧數為:"<<diGraph.arcNum<<endl<<endl;<br /> cout<<"鄰接表結構如下"<<endl;<br /> ArcNode* node = NULL;<br /> for(int i=0;i<diGraph.vexNum;i++){<br /> cout<<diGraph.vertices[i].data<<":";<br /> node = diGraph.vertices[i].fristArc;<br /> while(node != NULL){<br /> cout<<"("<<node->adjvex<<","<<node->info<<") ; ";<br /> node = node->nextArc;<br /> }<br /> cout<<endl;<br /> }<br /> return true;<br />}</p><p>#ifdef _NON_RECURSION_TRAVERSE<br />/*深度優先非遞迴遍曆有向圖,利用棧*/<br />bool Depth_First_Traverse(Graph* pDiGraph){<br /> for(int i=0;i<pDiGraph->vexNum;i++){ //初始化,全為false<br /> pDiGraph->vertices[i].isVisited = false;<br /> }<br /> VNode* vnode;<br /> stack<VNode*> TraverseStack; //用stack實現非遞迴遍曆演算法<br /> TraverseStack.push(&(pDiGraph->vertices[0])); //第一個節點入棧</p><p> while(!TraverseStack.empty()){<br /> vnode = (VNode*)TraverseStack.top(); //獲得棧頂節點<br /> vnode->isVisited = true;<br /> cout<<"遍曆:"<<vnode->data<<endl;<br /> TraverseStack.pop();<br /> ArcNode* node = vnode->fristArc;<br /> while(node != NULL){<br /> if(!(pDiGraph->vertices[node->adjvex]).isVisited){<br /> TraverseStack.push(&(pDiGraph->vertices[node->adjvex])); //入棧<br /> }<br /> node = node->nextArc;<br /> }<br /> }<br /> return true;<br />}<br />#endif</p><p>#ifdef _RECURSION_TRAVERSE<br />/*深度優先遞迴遍曆時,用來遍曆每一個頂點*/<br />bool DFT(Graph* pDiGraph,bool* visited,int i){<br /> if(!visited[i]){<br /> visited[i] = true; //標誌該頂點已被訪問了<br /> cout<<"遍曆:"<<pDiGraph->vertices[i].data<<endl;<br /> ArcNode* node = pDiGraph->vertices[i].fristArc;//遍曆其臨街單鏈表<br /> while(node != NULL){<br /> DFT(pDiGraph,visited,node->adjvex);<br /> node = node->nextArc;<br /> }<br /> }<br /> return true;<br />}</p><p>/*深度優先遞迴遍曆有向圖*/<br />bool Depth_First_Traverse(Graph* pDiGraph){<br /> int size = pDiGraph->vexNum; //頂點數目<br /> bool* visited = new bool[size]; //訪問標誌數組<br /> for(int i = 0;i < size;i++){ //初始化,全為false<br /> visited[i] = false;<br /> }<br /> for(int i = 0;i<size;i++){ //<br /> DFT(pDiGraph,visited,i);<br /> }<br /> delete[] visited;<br /> return true;<br />}<br />#endif</p><p>#ifdef _NON_RECURSION_TRAVERSE<br />/*廣度優先非遞迴遍曆有向圖,利用隊列*/<br />bool Breadth_First_Traverse(Graph* pDiGraph){<br /> for(int i=0;i<pDiGraph->vexNum;i++){ //初始化,全為false<br /> pDiGraph->vertices[i].isVisited = false;<br /> }<br /> VNode* vnode;<br /> queue<VNode*> TraverseQueue; //用queue實現非遞迴遍曆演算法<br /> TraverseQueue.push(&(pDiGraph->vertices[0])); //第一個節點入隊</p><p> while(!TraverseQueue.empty()){<br /> vnode = (VNode*)TraverseQueue.front(); //獲得隊首節點<br /> vnode->isVisited = true;<br /> cout<<"遍曆:"<<vnode->data<<endl;<br /> TraverseQueue.pop();<br /> ArcNode* node = vnode->fristArc;<br /> while(node != NULL){<br /> if(!(pDiGraph->vertices[node->adjvex]).isVisited){<br /> TraverseQueue.push(&(pDiGraph->vertices[node->adjvex])); //入隊<br /> }<br /> node = node->nextArc;<br /> }<br /> }<br /> return true;<br />}<br />#endif</p><p>#ifdef _RECURSION_TRAVERSE<br />/*廣度優先遞迴遍曆時,用來遍曆每一個頂點*/<br />bool BFT(Graph* pDiGraph,bool* visited,int i){<br /> if(!visited[i]){<br /> visited[i] = true; //標誌該頂點已被訪問了<br /> cout<<"遍曆:"<<pDiGraph->vertices[i].data<<endl;<br /> ArcNode* node = pDiGraph->vertices[i].fristArc;//遍曆其臨街單鏈表<br /> while(node != NULL){<br /> if(!pDiGraph->vertices[node->adjvex].isVisited){<br /> pDiGraph->vertices[node->adjvex].isVisited = true;<br /> cout<<"遍曆:"<<pDiGraph->vertices[node->adjvex].data<<endl;<br /> }<br /> node = node->nextArc;<br /> // BFT(pDiGraph,visited,node->adjvex);<br /> }<br /> BFT(pDiGraph,visited,node->adjvex);<br /> }<br /> return true;<br />}<br />/*廣度優先遞迴遍曆有向圖*/<br />bool Breadth_First_Traverse(Graph* pDiGraph){<br /> int size = pDiGraph->vexNum; //頂點數目<br /> bool* visited = new bool[size]; //訪問標誌數組<br /> for(int i = 0;i < size;i++){ //初始化,全為false<br /> visited[i] = false;<br /> }<br /> for(int i = 0;i<size;i++){ //<br /> BFT(pDiGraph,visited,i);<br /> }<br /> delete[] visited;<br />}<br />#endif</p><p>int main()<br />{<br /> Graph diGraph; //有向圖<br /> Graph udiGraph; //無向圖</p><p> InitDiGraph(&diGraph); //初始化有向圖,構建</p><p> DisplayDiGraph(diGraph); //顯示該有向圖</p><p> cout<<endl<<"***************深度優先遍曆結果***********"<<endl;<br /> Depth_First_Traverse(&diGraph); //深度優先遍曆</p><p> cout<<endl<<"***************廣度優先遍曆結果***********"<<endl;<br /> Breadth_First_Traverse(&diGraph); //廣度優先遍曆</p><p> return 0;<br />}<br />

 

程式運行結果

0 表示有向圖

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.