图的两种遍历:深度优先遍历+广度优先遍历

这篇具有很好参考价值的文章主要介绍了图的两种遍历:深度优先遍历+广度优先遍历。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

一、深度优先遍历

1、简介

深度优先遍历是指按照深度方向搜索,它类似于树的先根遍历,是树的先根遍历的推广。

基本思想(通俗)

选一条路走到 ,直到 走不通,就 原路返回看看 是否还有路可走,如果返回到起点还无路可走,说明深度优先遍历已完成。

2、举例说明

这是要深度遍历的无向图

 图的两种遍历:深度优先遍历+广度优先遍历

 深度遍历依次访问的为:

v1->v2->v4->v8->v5->v3->v6->v7

3、C语言代码 

(1)邻接矩阵存储无向图。

1 2 3 4 5 6 7 8
1 0 1 1 0 0 0 0 0
2 1 0 0 1 1 0 0 0
3 1 0 0 0 0 1 1 0
4 0 1 0 0 0 0 0 1
5 0 1 0 0 0 0 0 1
6 0 0 1 0 0 0 0 0
7 0 0 1 0 0 0 0 0
8 0 0 0 1 1 0 0 0

对于图的存储,请参考我的文章:图的三种存储结构:邻接矩阵表示法+链表法+十字链表法

存储无向图

图的两种遍历:深度优先遍历+广度优先遍历

#include<stdio.h>
#include<stdlib.h>
#define MAX_VERTEM_NUM 10 
#define INFINITY 32768
 
typedef enum{
	DG,DN,UDG,UDN	
}graghKind;
//digraph  DG有向图
//directed network  DN有向网
//undirected graph  UDG无向图
//undirected network  UDN无向网
 
typedef char vertemData;
 
typedef struct {
	vertemData vert[MAX_VERTEM_NUM];			//顶点向量
	int adj[MAX_VERTEM_NUM][MAX_VERTEM_NUM];	//邻接矩阵
	int vertNum,arcNum;							//图的顶点数和弧数
	graghKind gragh;							//图的类型
}adjMatrix;
 
//求顶点位置
int locateVertem(adjMatrix *G,vertemData v){
	for(int j=0;j<G->vertNum;j++)
	{
		if(G->vert[j]==v)
		{
			return j;
		}
	}
}
 
//创建无向图
int creatUDG(adjMatrix *G){
	int i,j,k,weight;
	vertemData v1,v2;
	printf("请输入图的顶点数和弧数:\n");
	scanf("%d %d",&G->vertNum,&G->arcNum);
	for(i=0;i<G->vertNum;i++)
		for(j=0;j<G->vertNum;j++)
			G->adj[i][j] = 0;	
	for(i=0;i<G->vertNum;i++)
	{
		printf("请输入图的顶点%d:\n",i);
		getchar();
		scanf("%c",&G->vert[i]);
	}
	for(k=0;k<G->arcNum;k++){
		printf("请输入弧%d的两个顶点:\n",k);
		getchar();
		scanf("%c %c",&v1,&v2);
		i = locateVertem(G,v1);
		j = locateVertem(G,v2);
		G->adj[i][j] = 1;
		G->adj[j][i] = 1;
	}
	printf("\n无向图存储完毕!\n\n");	
	return 0;
}

运行结果

图的两种遍历:深度优先遍历+广度优先遍历

图的两种遍历:深度优先遍历+广度优先遍历

(2) 用一个数组去存储已访问点的信息

0 1 2 3 4 5 6 7
0 0 0 0 0 0 0 0

0代表该点未访问,1代表该点访问了。

图的两种遍历:深度优先遍历+广度优先遍历

(3)深度遍历的算法描述

  • 更新访问点数组信息,在邻接矩阵当中找到该访问点的最近的邻接点,访问该邻接点,输出遍历顶点信息,重复此步骤。
  • 当无法继续深度遍历的时候,在访问点数组中往后依次退1,直到能有一个顶点能继续深度遍历。
  • 当起点都无法继续深度遍历的时候,对图的深度遍历已完成

实际就是从第n个顶点开始、标记该顶点已被访问,然后查找该顶点第一个未访问的邻接点第i个顶点,再去第i个顶点 深度遍历。

实际就是一个递归的过程。

//深度遍历无向图
void depth_first_traversal_UDG(adjMatrix *G,int *v,int n)
{
	int i;
	if(G==NULL) return;
	if(n<0||n>G->vertNum) return;
	v[n] = 1;
	if(n==0) printf("%c",G->vert[n]);
	else printf("->%c",G->vert[n]);
	for(i=0;i<G->vertNum;i++)
		if(G->adj[n][i]!=0&&v[i]!=1) depth_first_traversal_UDG(G,v,i);	
}

(4)完整代码 

#include<stdio.h>
#include<stdlib.h>
#define MAX_VERTEM_NUM 10 
#define INFINITY 32768
 
typedef enum{
	DG,DN,UDG,UDN	
}graghKind;
//digraph  DG有向图
//directed network  DN有向网
//undirected graph  UDG无向图
//undirected network  UDN无向网
 
typedef char vertemData;
 
typedef struct {
	vertemData vert[MAX_VERTEM_NUM];			//顶点向量
	int adj[MAX_VERTEM_NUM][MAX_VERTEM_NUM];	//邻接矩阵
	int vertNum,arcNum;							//图的顶点数和弧数
	graghKind gragh;							//图的类型
}adjMatrix;
 
//求顶点位置
int locateVertem(adjMatrix *G,vertemData v){
	for(int j=0;j<G->vertNum;j++)
	{
		if(G->vert[j]==v)
		{
			return j;
		}
	}
}
 
//创建无向图
int creatUDG(adjMatrix *G){
	int i,j,k,weight;
	vertemData v1,v2;
	printf("请输入图的顶点数和弧数:\n");
	scanf("%d %d",&G->vertNum,&G->arcNum);
	for(i=0;i<G->vertNum;i++)
		for(j=0;j<G->vertNum;j++)
			G->adj[i][j] = 0;	
	for(i=0;i<G->vertNum;i++)
	{
		printf("请输入图的顶点%d:\n",i);
		getchar();
		scanf("%c",&G->vert[i]);
	}
	for(k=0;k<G->arcNum;k++){
		printf("请输入弧%d的两个顶点:\n",k);
		getchar();
		scanf("%c %c",&v1,&v2);
		i = locateVertem(G,v1);
		j = locateVertem(G,v2);
		G->adj[i][j] = 1;
		G->adj[j][i] = 1;
	}
	printf("\n无向图存储完毕!\n\n");	
	return 0;
}
 
//深度遍历无向图
void depth_first_traversal_UDG(adjMatrix *G,int *v,int n)
{
	int i;
	if(G==NULL) return;
	if(n<0||n>G->vertNum) return;
	v[n] = 1;
	if(n==0) printf("%c",G->vert[n]);
	else printf("->%c",G->vert[n]);
	for(i=0;i<G->vertNum;i++)
		if(G->adj[n][i]!=0&&v[i]!=1) depth_first_traversal_UDG(G,v,i);	
}
 
int main(){
	adjMatrix *G = (adjMatrix*)malloc(sizeof(adjMatrix));
	creatUDG(G);
	int visited[G->vertNum]={0};
	printf("深度优先遍历无向图:\n");
	depth_first_traversal_UDG(G,visited,0);
	return 0;
}

运行结果

图的两种遍历:深度优先遍历+广度优先遍历

 附

图的两种遍历:深度优先遍历+广度优先遍历

图的两种遍历:深度优先遍历+广度优先遍历

二、广度优先遍历

1、简介

广度优先搜索是指按照广度方向搜索,它类似于树的按层次遍历,是树的按层次遍历的推广。

基本思想(通俗)

把一层的邻接点访问完后再去访问下一层。

2、举例说明

这是要广度遍历的无向图

图的两种遍历:深度优先遍历+广度优先遍历

对无向图进行广度优先遍历:

v1->v2->v3->v4->v5->v6->v7->v8 

3、C语言代码

(1)算法描述

当访问到n层的时候,依次入队列,出队列的顶点访问其邻接点并入队列。

广度遍历上图的情况下队列的变化如下:

1
2 3
3 4 5
4 5 6 7
5 6 7 8
6 7 8
7 8
8

(2)完整代码

#include<stdio.h>
#include<stdlib.h>
#define MAX_VERTEM_NUM 10 
 
typedef enum{
	DG,DN,UDG,UDN	
}graghKind;
//digraph  DG有向图
//directed network  DN有向网
//undirected graph  UDG无向图
//undirected network  UDN无向网
 
typedef char vertemData;
int visited[MAX_VERTEM_NUM] = {0};//访问数组
 
/*邻接矩阵*/
typedef struct {
	vertemData vert[MAX_VERTEM_NUM];			//顶点向量
	int adj[MAX_VERTEM_NUM][MAX_VERTEM_NUM];	//邻接矩阵
	int vertNum,arcNum;							//图的顶点数和弧数
	graghKind gragh;							//图的类型
}adjMatrix;
 
/*队列结构*/
typedef struct QNode
{
	vertemData data;
	struct QNode *next;
}QNode;
 
typedef struct
{
	QNode *front,*rear;  //队头队尾指针 
}LinkQueue;
 
/*求顶点位置*/
int locateVertem(adjMatrix *G,vertemData v){
	for(int j=0;j<G->vertNum;j++)
	{
		if(G->vert[j]==v)
		{
			return j;
		}
	}
}
 
/*创建无向图*/
int creatUDG(adjMatrix *G){
	int i,j,k,weight;
	vertemData v1,v2;
	printf("请输入图的顶点数和弧数:\n");
	scanf("%d %d",&G->vertNum,&G->arcNum);
	for(i=0;i<G->vertNum;i++)
		for(j=0;j<G->vertNum;j++)
			G->adj[i][j] = 0;	
	for(i=0;i<G->vertNum;i++)
	{
		printf("请输入图的顶点%d:\n",i);
		getchar();
		scanf("%c",&G->vert[i]);
	}
	for(k=0;k<G->arcNum;k++){
		printf("请输入弧%d的两个顶点:\n",k);
		getchar();
		scanf("%c %c",&v1,&v2);
		i = locateVertem(G,v1);
		j = locateVertem(G,v2);
		G->adj[i][j] = 1;
		G->adj[j][i] = 1;
	}
	printf("\n无向图存储完毕!\n\n");	
	return 0;
}
 
/*创建空队列*/
int init_queue(LinkQueue *L)
{
	L->front=L->rear=(QNode*)malloc(sizeof(QNode));
	if(!L->front) return 0;
	L->front->next=NULL;
	return 0;	
}
 
/*判断队列是否为空*/
int empty_queue(LinkQueue *L)
{
	if(L->front->next==NULL) return 1;
	else return 0;
}
 
/*入队列*/
int in_queue(LinkQueue *L,int n)
{
	QNode *t = (QNode*)malloc(sizeof(QNode));
	if(!t) exit(0);
	t->data = n;
	t->next = NULL;
	L->rear->next = t;
	L->rear = t;
	free(t);
	return 0;
}
 
/*出队列*/
int out_queue(LinkQueue *L)
{
	QNode *t;
	if(L->front==L->rear) return 0;
	t = L->front->next;
	L->front->next = t->next;
	if(t==L->rear) L->rear = L->front;
	return 1;
}
 
/*广度遍历*/
int BFS_traverse_UDN(adjMatrix *G)
{
	int i=0,j;
	LinkQueue *L = (LinkQueue*)malloc(sizeof(LinkQueue));
	init_queue(L);
	printf("广度遍历无向图:");
	visited[i] = 1;
	printf("%c",G->vert[i]);
	in_queue(L,i);
	do
	{
		out_queue(L);
		for(j=0;j<G->vertNum;j++)
		{
			if(G->adj[i][j]!=0&&visited[j]!=1)
			{
				visited[j] = 1;
				printf("->%c",G->vert[j]);
				in_queue(L,j);
			}
		}
		i++;
	}while(!empty_queue(L));	
	free(L);
	return 0;
}
 
int main()
{
	adjMatrix *G = (adjMatrix*)malloc(sizeof(adjMatrix));
	creatUDG(G);
	BFS_traverse_UDN(G);
	return 0;
}

图的两种遍历:深度优先遍历+广度优先遍历

图的两种遍历:深度优先遍历+广度优先遍历

图的两种遍历:深度优先遍历+广度优先遍历文章来源地址https://www.toymoban.com/news/detail-464288.html

到了这里,关于图的两种遍历:深度优先遍历+广度优先遍历的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 图的遍历-深度优先遍历与广度优先遍历(C语言)

    图的遍历 概念:指的是从图中的任一顶点出发,对图中的所有顶点访问一次且只访问一次。 邻接矩阵及邻接表的创建 : 图的存储结构-无向邻接矩阵与无向邻接表(C语言). 结构定义 邻接矩阵的深度优先遍历操作 邻接矩阵的深度优先递归算法 结构定义 邻接表的深度优先遍

    2024年02月06日
    浏览(48)
  • 大话数据结构-图的深度优先遍历和广度优先遍历

      图的遍历分为深度优先遍历和广度优先遍历两种。   深度优先遍历(Depth First Search),也称为深度优先搜索,简称DFS,深度优先遍历,是指从某一个顶点开始,按照一定的规则,访问并记录下一个未访问顶点。对于非连通图,则是按连通分量,采用同一规则进行深度优

    2024年02月04日
    浏览(58)
  • 图的遍历之 深度优先搜索和广度优先搜索

    深度优先搜索的图文介绍 1. 深度优先搜索介绍 图的深度优先搜索(Depth First Search),和树的先序遍历比较类似。 它的思想:假设初始状态是图中所有顶点均未被访问,则从某个顶点v出发,首先访问该顶点,然后依次从它的各个未被访问的邻接点出发深度优先搜索遍历图,直至

    2024年02月13日
    浏览(52)
  • 蛮力算法之深度优先遍历和广度优先遍历——图的深度优先遍历和广度优先遍历,附带案例:迷宫问题及矩阵中传染性传播问题

    这两种搜索方法本质上都是基于蛮力法思路 这两种搜索方法对有向图和无向图都适用 1.1 邻接矩阵 邻接矩阵示意图: 1.2 邻接表 注意:边结点代表的是图中的边,而并非图中的结点;头结点才表示图中的结点;头结点身后所连接的为边结点 邻接表示意图:(一般默认为出边

    2024年02月05日
    浏览(66)
  • (超详细)C++图的深度优先遍历、广度优先遍历(数据结构)

            根据下图,编写代码实现图的深度优先遍历和广度优先遍历。          按照英文字母顺序,以邻接表为存储结构,实现图的深度优先和广度优先遍历。遍历的顺序从顶点a开始。 以用户指定的结点为起点,分别输出每种遍历下的结点访问序列。   (1)从顶点a,

    2024年02月08日
    浏览(60)
  • 图详解第二篇:图的遍历(广度优先+深度优先)

    所谓图的遍历: 即从图中的任一顶点出发,对图中的所有顶点访问一次且只访问一次。 给定一个图G和其中任意一个顶点v0,从v0出发,沿着图中各边访问图中的所有顶点,且每个顶点仅被遍历一次。 ps: 我们后面讲解这些图相关的算法默认都针对邻接矩阵结构的图去讲解,

    2024年02月08日
    浏览(58)
  • 【数据结构与算法】图的深度优先和广度优先遍历

    😊😊作者简介😊😊 : 大家好,我是南瓜籽,一个在校大二学生,我将会持续分享Java相关知识。 🎉🎉个人主页🎉🎉 : 南瓜籽的主页 ✨✨座右铭✨✨ : 坚持到底,决不放弃,是成功的保证,只要你不放弃,你就有机会,只要放弃的人,他肯定是不会成功的人。 图是一

    2024年02月02日
    浏览(58)
  • 【数据结构】图的遍历:广度优先(BFS),深度优先(DFS)

    目录 1、广度优先(BFS) 算法思想  广度优先生成树  知识树  代码实现  2、深度优先(DFS) 算法思想  深度优先生成树 知识树  代码实现           图的广度优先遍历(BFS)是一种遍历图的算法,其思想是从起始顶点开始遍历图,先访问起始顶点的所有直接邻居,然

    2024年02月04日
    浏览(66)
  • 数据结构学习笔记——图的遍历算法(深度优先搜索和广度优先搜索)

    图的遍历指从图中某一顶点出发(任意一个顶点都可以作为访问的起始顶点),按照某种遍历方法,对图中所有的顶点访问一次且只访问一次。图与树不一样,其中一个顶点可能与多个顶点相连,所以需记录已访问过的顶点,当访问一个顶点后,考虑如何选取下一个要访问的

    2024年02月05日
    浏览(53)
  • 图的遍历(搜索)算法(深度优先算法DFS和广度优先算法BFS)

    从图的某个顶点出发访问遍图中所有顶点,且每个顶点仅被访问一次。(连通图与非连通图) 1、访问指定的起始顶点; 2、若当前访问的顶点的邻接顶点有未被访问的,则任选一个访问之;反之,退回到最近访问过的顶点;直到与起始顶点相通的全部顶点都访问完毕; 3、若

    2024年01月17日
    浏览(48)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包