多多色-多人伦交性欧美在线观看-多人伦精品一区二区三区视频-多色视频-免费黄色视屏网站-免费黄色在线

國內最全IT社區平臺 聯系我們 | 收藏本站
阿里云優惠2
您當前位置:首頁 > php開源 > php教程 > 數據結構(C實現)------- 圖的深度優先遍歷

數據結構(C實現)------- 圖的深度優先遍歷

來源:程序員人生   發布時間:2015-01-19 08:22:09 閱讀次數:4354次

[本文是自己學習所做筆記,歡迎轉載,但請注明出處:http://blog.csdn.net/jesson20121020]

算法描寫:      

       假定給定圖G的初始狀態是所有頂點均未曾訪問過,在G中任選1頂點vi為初始的動身點,則深度優先遍歷可定義以下: 首先訪問動身點vi,并將其標記為已被訪問過;然后,順次從vi動身遍歷vi的每個鄰接點vj,若vj未曾訪問過,則以vj為新的動身點繼續進行深度優先遍歷,直至圖中所有和vi有路徑相通的頂點都被訪問到為止。因此,若G是連通圖,則從初始動身點開始的遍歷進程結束也就意味著完成了對圖G的遍歷。

算法實現:

       分別以鄰接矩陣和鄰接表作為圖的存儲結構,給出連通圖的深度優先搜索遍歷的遞歸算法。算法描寫以下:

      (1) 訪問動身點vi,并將其標記為已被訪問已訪問過。

      (2) 遍歷vi的每個鄰接點vj,若vj未曾訪問過,則以vj為新的動身點繼續進行深度優先遍歷。

完全代碼:

      用鄰接矩陣實現深度優先搜索算法源代碼以下:

/** * 深度遍歷圖 **/ void DFS_MG(MGraph MG,int i){ visit[i] = 1; printf("%c ",MG.vexs[i]); int j; for (j = 1; j <= MG.vexnum;j++){ if(visit[j] == 0 && MG.arcs[i][j] == 1) DFS_MG(MG,j); } }
    

     用鄰接表實現深度優先搜索算法源代碼以下:

/** * 深度遍歷圖 **/ void DFS_AG(ALGraph AG,int i){ ArcPtr p; printf("%c ",AG.vertices[i].vexdata); visit[i] = 1; p = AG.vertices[i].firstarc; while( p!= NULL ){ if(visit[p->adjvex] == 0) DFS_AG(AG,p->adjvex); p = p->nextarc; } }


算法說明:

         對具有n個頂點,e條邊的連通圖,算法DFS_MG,DFS_AG 均調用n次。除初始調用是來自外部,基于n⑴次調用均是來自DFS_MG和DFS_AG內部的遞歸調用,用鄰接矩陣實現時,遍歷1個頂點的所有鄰接點需要O(n)時間,則遍歷全部圖需要O(n^2),即DFS_MG的時間復雜度為O(n^2)。

       用鄰接表實現時,遍歷n個頂點的所有鄰接點是對邊表節點的掃描1遍,故算法DFS_AG時間復雜度為O(n+e)。

          采取深度優先遍歷算法時,都要用到訪問標志,所以該算法的空間復雜度為O(n).

      

          鄰接矩陣實現深度優先搜索算法完全代碼以下:

/* ============================================================================ Name : Graph.c Author : jesson20121020 Version : 1.0 Description : create Graph using Adjacency Matrix, Ansi-style ============================================================================ */ #include <stdio.h> #include <stdlib.h> #define MAX_VEX_NUM 50 typedef char VertexType; typedef enum { DG, UDG } GraphType; typedef struct { VertexType vexs[MAX_VEX_NUM]; int arcs[MAX_VEX_NUM][MAX_VEX_NUM]; int vexnum, arcnum; GraphType type; } MGraph; //設置圖中頂點訪問標志 int visit[MAX_VEX_NUM]; /** * 根據名稱得到指定頂點在頂點集合中的下標 * vex 頂點 * return 如果找到,則返回下標,否則,返回0 */ int getIndexOfVexs(char vex, MGraph *MG) { int i; for (i = 1; i <= MG->vexnum; i++) { if (MG->vexs[i] == vex) { return i; } } return 0; } /** * 創建鄰接矩陣 */ void create_MG(MGraph *MG) { int i, j, k; int v1, v2, type; char c1, c2; printf("Please input graph type DG(0) or UDG(1) :"); scanf("%d", &type); if (type == 0) MG->type = DG; else if (type == 1) MG->type = UDG; else { printf("Please input correct graph type DG(0) or UDG(1)!"); return; } printf("Please input vexmun : "); scanf("%d", &MG->vexnum); printf("Please input arcnum : "); scanf("%d", &MG->arcnum); getchar(); for (i = 1; i <= MG->vexnum; i++) { printf("Please input %dth vex(char):", i); scanf("%c", &MG->vexs[i]); getchar(); } //初始化鄰接矩陣 for (i = 1; i <= MG->vexnum; i++) { for (j = 1; j <= MG->vexnum; j++) { MG->arcs[i][j] = 0; } } //輸入邊的信息,建立鄰接矩陣 for (k = 1; k <= MG->arcnum; k++) { printf("Please input %dth arc v1(char) v2(char) : ", k); scanf("%c %c", &c1, &c2); v1 = getIndexOfVexs(c1, MG); v2 = getIndexOfVexs(c2, MG); if (MG->type == 1) MG->arcs[v1][v2] = MG->arcs[v2][v1] = 1; else MG->arcs[v1][v2] = 1; getchar(); } } /** * 打印鄰接矩陣和頂點信息 */ void print_MG(MGraph MG) { int i, j; if(MG.type == DG){ printf("Graph type: Direct graph "); } else{ printf("Graph type: Undirect graph "); } printf("Graph vertex number: %d ",MG.vexnum); printf("Graph arc number: %d ",MG.arcnum); printf("Vertex set: "); for (i = 1; i <= MG.vexnum; i++) printf("%c ", MG.vexs[i]); printf(" Adjacency Matrix: "); for (i = 1; i <= MG.vexnum; i++) { j = 1; for (; j < MG.vexnum; j++) { printf("%d ", MG.arcs[i][j]); } printf("%d ", MG.arcs[i][j]); } } /** * 初始化頂點訪問標志 **/ void init_Visit(){ int i; for(i = 0;i < MAX_VEX_NUM;i++) visit[i] = 0; } /** * 深度遍歷圖 **/ void DFS_MG(MGraph MG,int i){ visit[i] = 1; printf("%c ",MG.vexs[i]); int j; for (j = 1; j <= MG.vexnum;j++){ if(visit[j] == 0 && MG.arcs[i][j] == 1) DFS_MG(MG,j); } } /** * 主函數 */ int main(void) { MGraph MG; create_MG(&MG); print_MG(MG); printf("The result of DFS: "); DFS_MG(MG,1); return EXIT_SUCCESS; }


       鄰接表實現深度優先搜索算法的完全代碼以下:

/* ============================================================================ Name : ALGraph.c Author : jesson20121020 Version : 1.0 Copyright : Your copyright notice Description : Graph using linkList, Ansi-style ============================================================================ */ #include <stdio.h> #include <stdlib.h> #include <stdio.h> #define MAX_VERTEX_NUM 50 typedef enum { DG, UDG } GraphType; typedef char VertexType; //表節點 typedef struct ArcNode { int adjvex; //鄰接節點 int weight; //邊權重 struct ArcNode *nextarc; //下1個節點指針 } ArcNode, *ArcPtr; //頭節點 typedef struct { VertexType vexdata; int id; ArcPtr firstarc; } VNode; //頭節點數組 typedef struct { VNode vertices[MAX_VERTEX_NUM]; int vexnum, arcnum; GraphType type; } ALGraph; int visit[MAX_VERTEX_NUM]; /** * 根據頂點字符得到在頂點數組中的下標 */ int getIndexOfVexs(char vex, ALGraph *AG) { int i; for (i = 1; i <= AG->vexnum; i++) { if (AG->vertices[i].vexdata == vex) { return i; } } return 0; } /** * 創建鄰接表 */ void create_AG(ALGraph *AG) { ArcPtr p,q; int i, j, k, type; VertexType v1, v2; printf("Please input graph type UG(0) or UDG(1) :"); scanf("%d", &type); if (type == 0) AG->type = DG; else if (type == 1) AG->type = UDG; else { printf("Please input correct graph type UG(0) or UDG(1)!"); return; } printf("please input vexnum:"); scanf("%d", &AG->vexnum); printf("please input arcnum:"); scanf("%d", &AG->arcnum); getchar(); for (i = 1; i <= AG->vexnum; i++) { printf("please input the %dth vex(char) : ", i); scanf("%c", &AG->vertices[i].vexdata); getchar(); AG->vertices[i].firstarc = NULL; } for (k = 1; k <= AG->arcnum; k++) { printf("please input the %dth arc v1(char) v2(char) :", k); scanf("%c %c", &v1, &v2); i = getIndexOfVexs(v1, AG); j = getIndexOfVexs(v2, AG); //根據圖的類型創建鄰接表 //方法1,插入到鏈表頭 /* if (AG->type == DG) { //有向圖 p = (ArcPtr) malloc(sizeof(ArcNode)); p->adjvex = j; p->nextarc = AG->vertices[i].firstarc; AG->vertices[i].firstarc = p; } else { //無向圖 p = (ArcPtr) malloc(sizeof(ArcNode)); p->adjvex = j; p->nextarc = AG->vertices[i].firstarc; AG->vertices[i].firstarc = p; p = (ArcPtr) malloc(sizeof(ArcNode)); p->adjvex = i; p->nextarc = AG->vertices[j].firstarc; AG->vertices[j].firstarc = p; } */ //方法2,插入到鏈表尾 if (AG->type == DG) { //有向圖 p = (ArcPtr) malloc(sizeof(ArcNode)); p->adjvex = j; //表為空 if(AG->vertices[i].firstarc == NULL){ AG->vertices[i].firstarc = p; } else{ //找最后1個表節點 q = AG->vertices[i].firstarc; while(q->nextarc != NULL){ q = q->nextarc; } q->nextarc = p; } p->nextarc = NULL; } else { //無向圖 p = (ArcPtr) malloc(sizeof(ArcNode)); p->adjvex = j; //表為空 if(AG->vertices[i].firstarc == NULL){ AG->vertices[i].firstarc = p; } else{ //找最后1個表節點 q = AG->vertices[i].firstarc; while(q->nextarc != NULL){ q = q->nextarc; } q->nextarc = p; } p->nextarc = NULL; p = (ArcPtr) malloc(sizeof(ArcNode)); p->adjvex = i; //表為空 if(AG->vertices[j].firstarc == NULL){ AG->vertices[j].firstarc = p; } else{ //找最后1個表節點 q = AG->vertices[j].firstarc; while(q->nextarc != NULL){ q = q->nextarc; } q->nextarc = p; } p->nextarc = NULL; } getchar(); } } /** * 輸出圖的相干信息 */ void print_AG(ALGraph AG) { ArcPtr p; int i; if (AG.type == DG) { printf("Graph type: Direct graph "); } else { printf("Graph type: Undirect graph "); } printf("Graph vertex number: %d ", AG.vexnum); printf("Graph arc number: %d ", AG.arcnum); printf("Vertex set : "); for (i = 1; i <= AG.vexnum; i++) printf("%c ", AG.vertices[i].vexdata); printf(" Adjacency List: "); for (i = 1; i <= AG.vexnum; i++) { printf("%d", i); p = AG.vertices[i].firstarc; while (p != NULL) { printf("-->%d", p->adjvex); p = p->nextarc; } printf(" "); } } /** * 初始化頂點訪問標志 **/ void init_Visit(){ int i; for(i = 0;i < MAX_VERTEX_NUM;i++) visit[i] = 0; } /** * 深度遍歷圖 **/ void DFS_AG(ALGraph AG,int i){ ArcPtr p; printf("%c ",AG.vertices[i].vexdata); visit[i] = 1; p = AG.vertices[i].firstarc; while( p!= NULL ){ if(visit[p->adjvex] == 0) DFS_AG(AG,p->adjvex); p = p->nextarc; } } int main(void) { ALGraph AG; create_AG(&AG); print_AG(AG); printf("The result of DFS: "); DFS_AG(AG,1); return EXIT_SUCCESS; }

生活不易,碼農辛苦
如果您覺得本網站對您的學習有所幫助,可以手機掃描二維碼進行捐贈
程序員人生
------分隔線----------------------------
分享到:
------分隔線----------------------------
關閉
程序員人生
主站蜘蛛池模板: 新午夜影院| 可以看的毛片网站 | 日韩亚洲欧美一区二区三区 | 国产片在线看 | 全黄冷激性性视频 | 中文字幕在线播放量 | 欧美18在线 | 永久免费毛片在线播放 | 亚洲欧美自拍另类图片色 | 国内久久久久久久久久 | 欧美精品亚洲精品日韩专区va | 黄色网址在线看 | 国产精品久久久久久网站 | 最新中文字幕在线 | 欧美一级手机免费观看片 | 日韩欧美一区二区中文字幕 | 国产一级做a爰片... | 亚洲免费视频在线 | jizz中文字幕 | h视频在线观看免费网站 | 欧美成人亚洲高清在线观看 | 国产一区二区三区不卡在线观看 | 91伊人网| 波多野结衣在线视频免费观看 | free性video另类重口 | 校园春色中文字幕 | 一区二区三区成人 | 日韩视频在线观看一区二区 | 久久久久欧美精品网站 | 欧美区一区二区三 | 亚洲视频在线观看地址 | 在线观看亚洲视频 | 日本乱妇| 欧美天堂久久 | 国产成人经典三级在线观看 | 亚洲精品成人一区二区 | 日韩精品视频一区二区三区 | 久久久亚洲欧洲日产国码606 | 操大逼网 | 亚色精品 | 在线播放国产一区 |