用C++实现图的DFS和BFS(邻接表)

概述

  图的储存方式有邻接矩阵和邻接表储存两种。由于邻接表的实现需要用到抽象数据结构里的链表,故稍微麻烦一些。C++自带的STL可以方便的实现List,使算法的实现变得简单起来

算法概述



  为了让我们的算法更有普适性,我们将非连通图也考虑在内。其实,要想遍历到类似于图中5,6节点这种孤岛节点,只需要依次按编号遍历顺序所有节点,如果某节点没有访问(book数组标记值为0),则从该节点开始深度优先搜索或广度优先搜索;等一次深搜或广搜完毕后,继续依次按照编号顺序遍历节点,选择从一个没访问过的结点开始再次深搜或广搜。。。如此知道把所有节点都遍历完。

代码

1.图抽象数据类型的声明,除了构造函数和析构函数之外,提供3个对外接口,分别实现递归DFS,BFS和非递归DFS(用STL栈实现)

using namespace std;
struct Graph{
//储存节点的邻接表
vector<list<int>> vertex;
//标记数组
bool book[100];
//n代表总节点个数
Graph(int n);
~Graph(); //对外接口,算法的驱动函数
void DFS_recursion_boost();
void BFS_boost();
void DFS_stack_boost(); private://内部算法实现
void DFS_recursion(int cur);
void BFS(int cur);
void DFS_stack(int cur); };

2.图的构造函数和析构函数实现

Graph::Graph(int n){
vertex.resize(n);
for(int i=0;i<n;++i){
int adj;
cout<<"请输入"<<i<<"号节点邻接链表(以-1表示结束输入)"<<endl;
cin>>adj;
while(adj!=-1){
vertex[i].push_back(adj);
cin>>adj;
}
}
memset(book,0,sizeof(book));
}
Graph::~Graph(){
vertex.clear();
}

3.图的递归DFS调用接口及其实现函数

void Graph::DFS_recursion_boost(){
for(int i=0;i<vertex.size();++i){
DFS_recursion(i);
}
} void Graph::DFS_recursion(int cur){
if(book[cur]==1) return;
book[cur]=1;
cout<<cur;
for(auto iter=vertex[cur].begin();iter!=vertex[cur].end();++iter){
if(book[*iter]==0){
DFS_recursion(*iter);
}
}
}

4.图的BFS调用接口及其实现函数


void Graph::BFS_boost(){
for(int i=0;i<vertex.size();++i){
BFS(i);
}
}
void Graph::BFS(int cur){
queue<int> q;
if(book[cur]==0){
q.push(cur);
}
while(!q.empty()){
int front=q.front();
q.pop();
cout<<front;
book[front]=1;
for(auto iter=vertex[front].begin();iter!=vertex[front].end();++iter){
if(book[*iter]==0){
q.push(*iter);
}
}
}
}

5.图的非递归DFS及其实现函数

void Graph::DFS_stack_boost(){
for(int i=0;i<vertex.size();++i){
DFS_stack(i);
}
}
void Graph::DFS_stack(int cur)
{
stack<int> s;
if(book[cur]==0){
s.push(cur);
}
while(!s.empty()){
int top=s.top();
if(book[top]==0){
book[top]=1;
cout<<top;
}
else{
s.pop();
// top=s.top();为何不要?
}
for(auto iter=vertex[top].begin();iter!=vertex[top].end();++iter){
if(book[*iter]==0){
s.push(*iter);
break;
}
}
}
}

6.主函数测试(注意,每次遍历后要把标记数组初始化为0)

int main(){
Graph G(7); cout<<"递归DFS:"<<endl;
G.DFS_recursion_boost();
memset(G.book,0,100);
cout<<endl; cout<<"BFS:"<<endl;
G.BFS_boost();
memset(G.book,0,100);
cout<<endl; cout<<"非递归BFS:"<<endl;
G.DFS_stack_boost();
memset(G.book,0,100);
cout<<endl;
system("pause");
return 0; }

输出

图的DFS和BFS(邻接表)的更多相关文章

  1. 数据结构(11) -- 邻接表存储图的DFS和BFS

    /////////////////////////////////////////////////////////////// //图的邻接表表示法以及DFS和BFS //////////////// ...

  2. 图的DFS与BFS

    图的DFS与BFS(C++) 概述 大一学生,作为我的第一篇Blog,准备记录一下图的基本操作:图的创建与遍历.请大佬多多包涵勿喷. 图可以采用邻接表,邻接矩阵,十字链表等多种储存结构进行储存,这里为 ...

  3. Java数据结构——图的DFS和BFS

    1.图的DFS: 即Breadth First Search,深度优先搜索是从起始顶点开始,递归访问其所有邻近节点,比如A节点是其第一个邻近节点,而B节点又是A的一个邻近节点,则DFS访问A节点后再访 ...

  4. 【数据结构】【图文】【oj习题】 图的拓扑排序(邻接表)

    拓扑排序: 按照有向图给出的次序关系,将图中顶点排成一个线性序列,对于有向图中没有限定次序关系的顶点,则可以人为加上任意的次序关系,由此所得顶点的线性序列称之为拓扑有序序列.显然对于有回路的有向图得不 ...

  5. 图的基本操作(基于邻接表):图的构造,深搜(DFS),广搜(BFS)

    #include <iostream> #include <string> #include <queue> using namespace std; //表结点 ...

  6. [数据结构]图的DFS和BFS的两种实现方式

    深度优先搜索 深度优先搜索,我们以无向图为例. 图的深度优先搜索(Depth First Search),和树的先序遍历比较类似. 它的思想:假设初始状态是图中所有顶点均未被访问,则从某个顶点v出发, ...

  7. 图的DFS与BFS遍历

    一.图的基本概念 1.邻接点:对于无向图无v1 与v2之间有一条弧,则称v1与v2互为邻接点:对于有向图而言<v1,v2>代表有一条从v1到v2的弧,则称v2为v1的邻接点. 2.度:就是 ...

  8. bfs 邻接表(需要优化 可能会RE *【模板】)

    //---基于邻接表的bfs #include <stdio.h> #include <string.h> #include <iostream> #include ...

  9. hdu 4707 Pet(DFS &amp;&amp; 邻接表)

    Pet Time Limit: 4000/2000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submis ...

随机推荐

  1. C# 泛型中的数据类型判定与转换

    提到类型转换,首先要明确C#中的数据类型,主要分为值类型和引用类型: 1.常用的值类型有:(struct) 整型家族:int,byte,char,short,long等等一系列 浮点家族:float, ...

  2. TeamX

    介绍 TeamX 是基于 SolonJT 平台构建的团队管理小工具,主要功能有: Wiki(团队词条,用于写MD格式接口文档也行...) Planned(项目计划 和 个人日志) Issues(问题管 ...

  3. Makefile中自动生成头文件依赖

    为什么需要自动生成头文件依赖? 编译单个源文件时,需要获取文件中包含的头文件的信息,但是一般的Makefile不会在规则中明确写明文件依赖的头文件,所以单独修改头文件后,不会导致包含头文件的源文件重新 ...

  4. ajax工作原理/实例

    ajax是什么? 是一种创建交互式网页应用的一种网页技术.简单来说,就是向服务器发起请求,获得数据使交互性和用户体验更好. ajax不是一种新的技术,是一些技术的集合体.有 1.XHTML和CSS 2 ...

  5. django-模板之标签

    目录 模板 模版是纯文本文件,可以生成任何基于文本的文件格式,比如HTML,XML,CSV等.Django模版语言致力于在性能和简单性上取得平衡.Django的模版系统并不是简单的将Python嵌入到 ...

  6. 数据库(十一):Navicat可视化工具

    进击のpython ***** 数据库--Navicat可视化工具 那命令行敲了那么久,难免影响开发效率 所以说就出现了一款可视化开发工具Navicat 下载位置:https://pan.baidu. ...

  7. 读/写docx文件

    安装 pip install python-docx 1.建立新Word文档 建立新文档需要调用Document对象的save方法,一个Document对象代表一个Word文档,该方法的参数是保存的文 ...

  8. FPGA内部IP核DDS

    项目当中需要正弦信号与余弦信号,首先想到了DDS芯片,例如AD9833.AD9834.由于还需要用FPGA   做一些数据处理,后来干脆直接用FPGA 内部的DDSIP核,同时根据IP核内部的相位累加 ...

  9. Python List list()方法

    描述 list() 方法用于将元组转换为列表.高佣联盟 www.cgewang.com 注:元组与列表是非常类似的,区别在于元组的元素值不能修改,元组是放在括号中,列表是放于方括号中. 语法 list ...

  10. asp.net mvc 模拟百度搜索

    页面代码: <td><span>*</span>车牌号码:</td> <td> <div id="search"& ...