图的遍历之深度优先算法伪代码描述(和树的前序遍历相似,实际上树可以看成特殊的图:N个顶点有N-1条边,不曾在回路!即树是图连通中最少边的情况)

图片来自网络

如上图:

深度优先遍历:

先选取一个顶点访问它,然后深度优先遍历它的每个未访问的邻接点

#include<stdlib.h>
#include<stdbool.h>
#include<stdio.h>
#define MaxVertexNum 100    /* 最大顶点数设为100 */
typedef int Vertex;         /* 用顶点下标表示顶点,为整型 */
typedef int WeightType;        /* 边的权值设为整型 */
typedef char DataType;        /* 顶点存储的数据类型设为字符型 */  bool Visited[MaxVertexNum];/* 边的定义 */
typedef struct ENode *PtrToENode;
struct ENode{  Vertex V1, V2;      /* 有向边<V1, V2> */  WeightType Weight;  /* 权重 */
};
typedef PtrToENode Edge;  /* 邻接点的定义 */
typedef struct AdjVNode *PtrToAdjVNode;
struct AdjVNode{  Vertex AdjV;        /* 邻接点下标 */  WeightType Weight;  /* 边权重 */  PtrToAdjVNode Next;    /* 指向下一个邻接点的指针 */
};  /* 顶点表头结点的定义 */
typedef struct Vnode{  PtrToAdjVNode FirstEdge;/* 边表头指针 */  DataType Data;            /* 存顶点的数据 */  /* 注意:很多情况下,顶点无数据,此时Data可以不用出现 */
} AdjList[MaxVertexNum];    /* AdjList是邻接表类型 */  /* 图结点的定义 */
typedef struct GNode *PtrToGNode;
struct GNode{    int Nv;     /* 顶点数 */  int Ne;     /* 边数   */  AdjList G;  /* 邻接表 */
};
typedef PtrToGNode LGraph; /* 以邻接表方式存储的图类型 */  LGraph CreateGraph( int VertexNum )
{ Vertex V;
/* 初始化一个有VertexNum个顶点但没有边的图 */
LGraph Graph=(LGraph)malloc(sizeof(struct GNode));
Graph->Nv=VertexNum;
Graph->Ne=0;/* 初始化邻接表头指针 */  /* 注意:这里默认顶点编号从0开始,到(Graph->Nv - 1) */  for (V=0; V<Graph->Nv; V++)  Graph->G[V].FirstEdge = NULL;  return Graph;
} void InsertEdge( LGraph Graph, Edge E )  {PtrToAdjVNode NewNode;  /* 插入边 <V1, V2> */  /* 为V2建立新的邻接点 */  NewNode = (PtrToAdjVNode)malloc(sizeof(struct AdjVNode));  NewNode->AdjV = E->V2;  NewNode->Weight = E->Weight;  /* 将V2插入V1的表头 */  NewNode->Next = Graph->G[E->V1].FirstEdge;  Graph->G[E->V1].FirstEdge = NewNode;  /* 若是无向图,还要插入边 <V2, V1> */  /* 为V1建立新的邻接点 */  NewNode = (PtrToAdjVNode)malloc(sizeof(struct AdjVNode));  NewNode->AdjV = E->V1;  NewNode->Weight = E->Weight;  /* 将V1插入V2的表头 */  NewNode->Next = Graph->G[E->V2].FirstEdge;  Graph->G[E->V2].FirstEdge = NewNode;  }LGraph BuildGraph()  {  LGraph Graph;  Edge E;  Vertex V;  int Nv, i;  scanf("%d", &Nv);   /* 读入顶点个数 */  Graph = CreateGraph(Nv); /* 初始化有Nv个顶点但没有边的图 */   scanf("%d", &(Graph->Ne));   /* 读入边数 */  if ( Graph->Ne != 0 ) { /* 如果有边 */   E = (Edge)malloc( sizeof(struct ENode) ); /* 建立边结点 */   /* 读入边,格式为"起点 终点 权重",插入邻接矩阵 */  for (i=0; i<Graph->Ne; i++) {  scanf("%d %d %d", &E->V1, &E->V2, &E->Weight);   /* 注意:如果权重不是整型,Weight的读入格式要改 */  InsertEdge( Graph, E );  }  free(E);}   /* 如果顶点有数据的话,读入数据 */  for (V=0; V<Graph->Nv; V++)   scanf(" %c", &(Graph->G[V].Data));  return Graph;  }  /* 邻接表存储的图 - DFS */void Visit( Vertex V ){printf("正在访问顶点%d\n", V);}/* Visited[]为全局变量,已经初始化为false */void DFS( LGraph Graph, Vertex V, void (*PVisit)(Vertex) ){   /* 以V为出发点对邻接表存储的图Graph进行DFS搜索 */PtrToAdjVNode W;(*PVisit)( V ); /* 访问第V个顶点 */Visited[V] = true; /* 标记V已访问 */for( W=Graph->G[V].FirstEdge; W; W=W->Next ) /* 对V的每个邻接点W->AdjV */if ( !Visited[W->AdjV] )    /* 若W->AdjV未被访问 */DFS( Graph, W->AdjV, PVisit );    /* 则递归访问之 */}int main(){for(int i=0;i<MaxVertexNum;i++)Visited[i]=false;//初始化为falseLGraph Graph=BuildGraph();DFS(Graph,0,Visit);return 0;}
#include<stdlib.h>
#include<stdbool.h>
#include<stdio.h>
#define MaxVertexNum 100    /* 最大顶点数设为100 */
#define INFINITY 65535        /* ∞设为双字节无符号整数的最大值65535*/
typedef int Vertex;         /* 用顶点下标表示顶点,为整型 */
typedef int WeightType;        /* 边的权值设为整型 */
typedef char DataType;        /* 顶点存储的数据类型设为字符型 */
bool Visited[MaxVertexNum];
/* 边的定义 */
typedef struct ENode *PtrToENode;
struct ENode{  Vertex V1, V2;      /* 有向边<V1, V2> */  WeightType Weight;  /* 权重 */
};
typedef PtrToENode Edge;  /* 图结点的定义 */
typedef struct GNode *PtrToGNode;
struct GNode{  int Nv;  /* 顶点数 */  int Ne;  /* 边数   */  WeightType G[MaxVertexNum][MaxVertexNum]; /* 邻接矩阵 */  DataType Data[MaxVertexNum];      /* 存顶点的数据 */  /* 注意:很多情况下,顶点无数据,此时Data[]可以不用出现 */
};
typedef PtrToGNode MGraph; /* 以邻接矩阵存储的图类型 */  MGraph CreateGraph( int VertexNum )
{ /* 初始化一个有VertexNum个顶点但没有边的图 */  Vertex V, W;  MGraph Graph;  Graph = (MGraph)malloc(sizeof(struct GNode)); /* 建立图 */  Graph->Nv = VertexNum;  Graph->Ne = 0;  /* 初始化邻接矩阵 */  /* 注意:这里默认顶点编号从0开始,到(Graph->Nv - 1) */  for (V=0; V<Graph->Nv; V++)  for (W=0; W<Graph->Nv; W++) if(V==W) Graph->G[V][W]=0;else  Graph->G[V][W] = INFINITY;  return Graph;
}  void InsertEdge( MGraph Graph, Edge E )  {/* 插入边 <V1, V2> */  Graph->G[E->V1][E->V2] = E->Weight;      /* 若是无向图,还要插入边<V2, V1> */  Graph->G[E->V2][E->V1] = E->Weight;  }MGraph BuildGraph()  {  MGraph Graph;  Edge E;  Vertex V;  int Nv, i;  scanf("%d", &Nv);   /* 读入顶点个数 */  Graph = CreateGraph(Nv); /* 初始化有Nv个顶点但没有边的图 */   scanf("%d", &(Graph->Ne));   /* 读入边数 */  if ( Graph->Ne != 0 ) { /* 如果有边 */   E = (Edge)malloc(sizeof(struct ENode)); /* 建立边结点 */   /* 读入边,格式为"起点 终点 权重",插入邻接矩阵 */  for (i=0; i<Graph->Ne; i++) {  scanf("%d %d %d", &E->V1, &E->V2, &E->Weight);   /* 注意:如果权重不是整型,Weight的读入格式要改 */  InsertEdge( Graph, E );  }  free(E);}   /* 如果顶点有数据的话,读入数据 */  for (V=0; V<Graph->Nv; V++)   scanf(" %c", &(Graph->Data[V]));  return Graph;  }  void Visit( Vertex V ){printf("正在访问顶点%d\n", V);}/* Visited[]为全局变量,已经初始化为false */void DFS( MGraph Graph, Vertex V, void (*PVisit)(Vertex) ){/* 以V为出发点对邻接表存储的图Graph进行DFS搜索 */(*PVisit)( V ); /* 访问第V个顶点 */Visited[V] = true; /* 标记V已访问 */for(Vertex W=0;W<Graph->Nv;W++)              if(!Visited[W]&&Graph->G[V][W]!=INFINITY&&V!=W) /* 对V的每个未被访问de邻接点*/DFS(Graph,W,PVisit);}int main(){for(int i=0;i<MaxVertexNum;i++)Visited[i]=false;//初始化为falseMGraph Graph=BuildGraph();DFS(Graph,0,Visit);return 0;}

用栈模拟

图的遍历之DSF深度优先算法6.2.1(网络整理)相关推荐

  1. 图的遍历(搜索)算法 之 深度优先遍历算法

    图的遍历的定义: 从图中的某个顶点出发访问遍图中的所有顶点,并且每个顶点仅仅被访问一次. 图的遍历算法我们常见的而且用的最多的就有两种:其一是图的深度优先遍历算法:其二是图的广度优先遍历算法.这里我们 ...

  2. 图的遍历之BSF广度优先算法6.2.2(网络整理)

    图的广度优先遍历和树的层序遍历相似,伪代码见下图: (以上图片来自网络) #include<stdlib.h> #include<stdbool.h> #include< ...

  3. c++ 遍历list_数据结构之图的遍历,一篇文章get全部考点

    图的概念 举个例子,假设你的微信朋友圈中有若干好友:张三.李四.王五.赵六.七大姑.八大姨. 而你七大姑的微信号里,又有若干好友:你.八大姨.Jack.Rose. 微信中,许许多多的用户组成了一个多对 ...

  4. 动画解析:图的遍历方式有哪些?

    点击关注上方"五分钟学算法", 设为"置顶或星标",第一时间送达干货. 转自景禹 小禹禹,你们好呀,景禹今天给你们说一说图的遍历方法! 小禹禹: 好呀好呀,图的 ...

  5. 分别用邻接矩阵和邻接表实现图的深度优先遍历和广度优先遍历_数据结构与算法学习笔记:图...

    图: 图结构区别于线性结构和树型结构,区别可见下图 逻辑上的图(graph)结构由顶点(vertex)和边(edge)组成. 一个图结构G包含顶点集合V和边集合E,任何两个顶点之间可以有一个边表示两者 ...

  6. 分别用邻接矩阵和邻接表实现图的深度优先遍历和广度优先遍历_数据结构与算法:三十张图弄懂「图的两种遍历方式」...

    原创: 进击的HelloWorld1 引言遍历是指从某个节点出发,按照一定的的搜索路线,依次访问对数据结构中的全部节点,且每个节点仅访问一次. 在二叉树基础中,介绍了对于树的遍历.树的遍历是指从根节点 ...

  7. 【小算法】图的遍历之深度优先(DFS)

    谈到算法,图的操作是避免不了. 而我们一般谈到图时,又必定会谈到图的遍历. 图的遍历通常有 2 种,深度优先(DFS) 和广度优先(BFS). 本篇博文讲解深度优先(DFS). 图的表示 图有两种表示 ...

  8. 数据结构学习笔记——图的遍历算法(深度优先搜索和广度优先搜索)

    目录 一.图的遍历概念 二.深度优先搜索(DFS) (一)DFS算法步骤 1.邻接表DFS算法步骤 2.邻接矩阵DFS算法步骤 (二)深度优先生成树.森林 (三)DFS的空间复杂度和时间复杂度 三.广 ...

  9. 获取图顶点的入度、出度;获取图的两个顶点之间的权值; 图的深度优先算法、图的广度优先遍历

    广度优先结果: 深度优先结果: 代码整理: public class Graph {private int vertexSize;//顶点数量private int[] vertexs;//顶点数组p ...

  10. 数据结构与算法(7-2)图的遍历(深度优先遍历DFS、广度优先遍历BFS)(分别用邻接矩阵和邻接表实现)

    目录 深度优先遍历(DFS)和广度优先遍历(BFS)原理 1.自己的原理图 2.官方原理图 一.邻接矩阵的深度优先遍历(DFS) 1.原理图 2. 过程: 3.总代码 二.邻接表的深度优先遍历(DFS ...

最新文章

  1. Nginx问题定位之监控进程异常退出
  2. 期望dp ---- B. Tree Array 思维+期望dp 逆序对期望数
  3. AI洞观 | 戴上红帽 看IBM冲杀云计算市场
  4. python的__init__几种方法总结【转载】
  5. Java-异常处理练习
  6. IntelliJ IDEA 快捷键(一)(window版)
  7. 在windows上搭建redis集群(Redis-Cluster)
  8. linuxpython源文件_Python3 源码安装(Linux 版)
  9. js嵌套函数内外层分别使用this关键字困局解
  10. 【笔记整理】电磁场复习——麦克斯韦四个方程组
  11. SketchUp 建筑分析图制作国外教程
  12. pythonwhile冒泡排序_python冒泡排序
  13. 用python做系统的感悟_《Python机器学习经典实例》学习感悟
  14. 病毒分析与防护实验3—— 反汇编工具(Ollydbg)的使用
  15. anaconda出现Multiple Errors Encountered.
  16. 人生有三重境界:看山是山,看水是水;看山不是山,看水不是水;看山还是山,看水还是水=
  17. 孙子兵法之36计详解
  18. 阿里云国际版服务器如何搭建区块链应用程序
  19. 【分享】集简云小程序识别名片到CRM流程搭建示例
  20. SQL DXP 6.6.x 高级版--最新版

热门文章

  1. 大数据技术栈思维导图
  2. MCSA / Windows Server 2016 DISM和Powershell管理和维护镜像
  3. 旧电脑再次起飞 分享一次联想Thinkpad X230黑苹果的完整过程
  4. efi分区咋移动到c盘里_efi系统分区是什么?重装系统EFI系统分区图文教程
  5. jQuery版本的区别
  6. js去除字符串头尾空格
  7. Anaconda配置OpenCV
  8. 【转载】AssetBundle资源打包加载管理
  9. matlab 折线图 标记_matlab画折线图标记线
  10. 大数运算——模加减运算