1. 程式人生 > >圖的深度優先遍歷DFS (鄰接矩陣實現) c語言

圖的深度優先遍歷DFS (鄰接矩陣實現) c語言

圖的遍歷是指從圖中的某一頂點出發,按照一定的策略訪問圖中的每一個頂點。每個頂點有且只能被訪問一次。

深度優先遍歷也叫深度優先搜尋(Depth First Search)。

它的遍歷規則:先選擇一個初始頂點,再規定一個方向,例如往右邊一直遍歷。於是就往右邊一直走,把訪問過的頂點做好標記,沿著右邊訪問完後,回溯到之前訪問過的頂點,找找還有沒有頂點沒有訪問的,當所有頂點被訪問,完成遍歷。

DFS是一個遞迴地將圖中所有頂點訪問的過程,類似於樹的前序遍歷。

用鄰接矩陣實現時需注意設定一個布林型別的訪問標誌陣列  visited

對於m個頂點e條邊的圖來說,由於鄰接矩陣是一個二維陣列,故時間複雜度O(㎡)

具體實現程式碼如下,

#include<stdio.h>
#include<stdlib.h>
//鄰接矩陣結構
typedef char VertexType;
typedef int EdgeType;

#define MAX 10
#define INFINITY 65535
#define TRUE 1
#define FALSE 0
typedef int Boole;  //布林型別 儲存TRUE FALSE
Boole visited[MAX];    //訪問標誌陣列 

typedef struct
{
	VertexType vexs[MAX];   //頂點表 
	EdgeType arc[MAX][MAX];   //鄰接矩陣 可看作邊表   
	int numVertexes,numEdges;
	int GraphType;  //圖的型別  無向0,有向1	
}MGraph;

//構造圖   有向圖和無向圖 
void create(MGraph *G)
{
	int i,j,k,w;
	printf("請輸入頂點數和邊數:\n");
	scanf("%d%d",&G->numVertexes,&G->numEdges);
	fflush(stdin);
	for(i=0;i<G->numVertexes;i++)     //建立頂點表
	{ 
		printf("\n第%d個頂點",i+1);
		scanf("%c",&G->vexs[i]);
		getchar();
	}
	
	for(i=0;i<G->numVertexes;i++)   //矩陣初始化 
		for(j=0;j<G->numVertexes;j++)
			G->arc[i][j]=INFINITY;
			
	for(k=0;k<G->numEdges;k++)
	{
		printf("輸入邊(Vi,Vj)的上下標i,j和權w(空格隔開):");
		scanf("%d%d%d",&i,&j,&w);
		G->arc[i][j]=w;
		if(G->GraphType==0)      //此時為無向圖   有向圖與無向的區別就只是這一行程式碼的有無 
		G->arc[j][i]=G->arc[i][j];
	}			 
} 

void Output(MGraph *G)     //輸出鄰接矩陣 
{
	int i,j,count=0;
	for(i=0;i<G->numVertexes;i++)
		printf("\t%c",G->vexs[i]);
	printf("\n");
	for(i=0;i<G->numVertexes;i++)
	{
		printf("%4c",G->vexs[i]);
		for(j=0;j<G->numVertexes;j++)
		{	
			
				printf("\t%d",G->arc[i][j]);
				count++;
				if(count%G->numVertexes==0)
				printf("\n");	
		} 
    }	 
 } 




/*深度優先遍歷*/



//深度優先遞迴演算法
void DFS(MGraph G,int i)
{
	int j;
	visited[i]=TRUE;   //被訪問的標記 
	printf("%c->",G.vexs[i]);
	for(j=0;j<G.numVertexes;j++)
	{
		if(G.arc[i][j]==1&&!visited[j])   //邊(i,j)存在且j頂點未被訪問,遞迴 
			DFS(G,j);
	} 
}

//深度優先遍歷
void DFStraverse(MGraph G)
{
	
	int i;
	for(i=0;i<G.numVertexes;i++)
		visited[i]=FALSE;
	for(i=0;i<G.numVertexes;i++)
			if(!visited[i])
				DFS(G,i);		
				
} 


int main()
{
	MGraph G;
	int i,j;
	printf("輸入生成圖的型別(無向圖0/有向圖1):");
	scanf("%d",&G.GraphType);
	create(&G);	
	printf("鄰接矩陣資料如下:\n");
	Output(&G);
	printf("\n");
	DFStraverse(G);
	printf("\n圖遍歷完畢");
	return 0;	 
}