5.1.2图的广度优先遍历

#include<iostream>
#include<cstdio>
using namespace std;
int book[101],sum,n,e[101][101];
void dfs(int cur){//cur是当前所在的顶点编号
	int i;
	cout<<cur<<" ";
	sum++;//每访问一个顶点,sum就加1
	if(sum==n){
		return;//所有的顶点都已经访问过则直接退出 
	} 
	for(i=1;i<=n;i++){//从1号顶点到n号顶点依次尝试,看哪些顶点与当前顶点cur有边相连 
		//判断当前顶点cur到顶点i是否有边,并判断顶点i是否已访问过
		if(e[cur][i]==1&&book[i]==0){
			book[i]=1;//标记顶点i已经访问过
			dfs(i);//从顶点i再出发继续遍历 
		} 
	} 
	return; 
} 
int main(){
	int i,j,n,m,a,b,cur,book[101]={0},e[101][101];
	int head,tail,que[10001];

	cout<<"请输入n m"<<endl<<"表示有n个结点,共有m条边:"<<endl;
	cin>>n>>m;
	//初始化二维矩阵
	for(i=1;i<=n;i++){
		for(j=1;j<=n;j++){
			if(i==j){
				e[i][j]=0;
			}
			else{
				e[i][j]=99999999;//我们这里假设99999999为正无穷 
			}
		}
	} 
	
	cout<<"请输入a b,表示结点a和结点b之间有边:"<<endl;
	//读入顶点之间的边 
	for(i=1;i<=m;i++){
		cin>>a>>b;
		e[a][b]=1; 
		e[b][a]=1;//这里是无向图,所以e[b][a]也赋值为1 
	} 
		
	//显示原始图的抽象矩阵
	cout<<endl<<"原始图对应的抽象矩阵为:"<<endl;//n个结点,形成n*n二维矩阵 
	for(i=1;i<=n;i++){
		for(j=1;j<=n;j++){
			printf("%10d",e[i][j]);
			if(j==n){
				cout<<endl;
			}
		}
	} 
	//队列初始化
	head=tail=1;
	
	//从1号顶点出发,将1号顶点加入队列
	que[tail]=1;
	cout<<endl<<"//**出发结点(搜索的首结点)"<<que[tail]<<"号已入队"<<"**//"<<endl;
	tail++;
	book[1]=1;//标记1号城市已访问 

	//当队列不为空时循环
	while(head<tail){
		cur=que[head];//当前正在访问的顶点编号
		cout<<endl<<"当前扩展的结点为:"<<cur<<endl; 
		for(j=1;j<=n;j++){//从1~n依次尝试
			//从顶点cur到顶点j是否有边并且结点j是否已访问过 
			if(e[cur][j]==1&&book[j]==0){
				//如果从顶点cur到顶点j是否有边并且结点j没被访问过,则将j号结点入队
				que[tail]=j;
				cout<<"//**"<<que[tail]<<"号结点已入队"<<"**//"<<endl;
				tail++;
				//标记结点j已被访问 
				book[j]=1; 
			} 
			//如果tail>n,则表明所有顶点都已经被访问过,任务结束,退出循环
			if(tail>n){
				break; 
			} 
		
		}
		head++;//注意这地方,千万不要忘记只有当一个结点扩展结束后,head++,然后才能继续扩展 
	} 
	
	//注意tail是指向队列队尾(即最后一位)的下一个位置,所以这儿需要-1
	cout<<endl<<endl<<"使用广度优先搜索的访问顺序为://** ";
	for(i=1;i<tail;i++){
		cout<<que[i]<<" ";
	} 
	cout<<"**//"<<endl;
	getchar(); 
	return 0;	
}

/*
	广度优先搜索核心思想为:
		首先以一个未被访问过的顶点作为起始顶点,访问其所有相邻的顶点;然后对每个相邻的顶点,
	再访问它们相邻的未被访问过的顶点,直到所有的顶点都被访问过。 
*/


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值