数据结构与算法基础(王卓)(24):深度优先遍历算法DFS和广度优先遍历算法BFS

news/2024/7/20 21:26:36 标签: 算法, 深度优先, 宽度优先

深度优先遍历算法DFS:

邻接矩阵:

#include<iostream>
using namespace std;

typedef int Status;
#define MaxInt 999999  //表示无穷大
#define MVNum 100  //最大顶点数
//MAX Vertex Number
typedef char VertexType;  //设顶点类型:字符型
typedef int ArcType;  //设边的权值类型:int型

struct AMG
{
    VertexType vex[MVNum];  //顶点表
    ArcType arc[MVNum][MVNum];  //邻接矩阵
    int VexNum, ArcNum;  //(图)当前:顶点数和边数
};  //Adjacency Matrix Graph

//深度优先遍历算法(邻接矩阵)
int visited[MVNum] = {};    //未访问时元素全部为空

void DFS(AMG G, int v)
{
    int w;
    //访问第v个结点
    cout << G.vex[v]; //输出顶点内容
    //cout << v << endl;
    visited[v] = 1;
    //依次检查邻接矩阵v所在的行
    for (w = 0; w < G.VexNum; w++)
        //从邻接矩阵的第v行的第1个元素开始-遍历到该行第n个元素
    {
        if ((G.arc[v][w] != 0) && !visited[w])
            //相连且未被访问过
            DFS(G, w);
    }
        //算法时间复杂度O(n^2)
}

int main()
{

}

邻接表:

一开始我写的(第一版):

void DFS(ALG G, int v)
{
    int w,i=0;
    ArcNode* p=G.vex->firstarc;
    //访问第v个结点
    while (i < v)
    {
        p = p->nextarc;
        i++;
    }
    cout << p->adjvex; //输出顶点内容位置
    visited[v] = 1;
    //依次检查邻接矩阵v所在的行
    for (w = 0; w < G.vexnum; w++)
        //从邻接矩阵的第v行的第1个元素开始-遍历到该行第n个元素
    {
        p = p->nextarc;
        if ((p->adjvex) && !visited[w])
//        if ((G.vex[v][w] != 0) && !visited[w])
            //相连且未被访问过
            DFS(G, w);
    }  
}

这里,我们犯(陷入)了许多个逻辑错误

问题:

(1):

我们写的函数:在一开始指向的,并不是第 i 个顶点,而是第一个顶点的第 i 个元素

更何况我们第一步要输出的,是一个顶点,而非一个边结点

(2):

在最后的判断语句最好还是新设立一个指针变量,要不然后面我感觉p容易变混乱了

 哈哈哈扯淡的,后面其实根本不需要这个玩意 


最终成品:

//深度优先遍历算法
int visited[MVNum] = {};    //未访问时元素全部为空
void DFS(ALG G, int v)
{
    int w,i=0;
    cout << G.vex[v].data; 
    visited[v] = 1;
    ArcNode* p = G.vex[v].firstarc;
    while (p != NULL)
    {
        if (visited[p->adjvex] != 0)
            DFS(G,p->adjvex);
        p = p->nextarc;
    }
}

By the way,复习一下链表【取第i个元素】:

Status 取第i个元素(LinkList L, int i, Elemtype e)
{// GetElem“i”
    LinkList p;
    p = L->next;
    int j = 1;
    while (p && i > j)
    {
        p = p->next;
        j++;
    }
    if (i < 0 || i < j || !p)
        return false;
    e = p->data;
    return true;
}


广度优先遍历算法BFS

breadth:宽度;(知识、兴趣等的)广泛

邻接表:


我写的:

int visited[MVNum] = {};    
void BFS(ALG G, int v)
{
    cout << G.vex[v].data;
    visited[v] = 1;
    SqQueue Q;
    InitQueue(Q);
    EnQueue(Q, G.vex[v].firstarc->adjvex);//从第一个顶点开始遍历
    auto i = G.vex[v].firstarc;//指向(代表)链头
    while (!QueneEmpty(Q))//直至队空结束
    {
        auto j = i;//用于指向访问各个元素节点
        while (j != NULL)//当结点为空(链尾,结束了)结束循环
        {
            if (visited[j->adjvex] == 0)//入队【没被访问过的】元素
            {
                EnQueue(Q, j->adjvex);
            }
            j = j->nextarc;//指向下一轮循环
            visited[j->adjvex] = 1;//别忘了
        }
        DeQueue(Q, i->adjvex);//出队队头
        cout << j->adjvex;
        //输出出队的元素,当然这里出队和输出在循环开始时操作也可以
    }
}

详细学习过程以及整个过程中所有踩的坑,详见:

数据结构与算法基础(王卓)(24)附:邻接表的广度优先遍历算法BFS(学习过程记录)_宇 -Yu的博客-CSDN博客


邻接矩阵:

void BFS(AMG& G)
{
    for (int v = 0; v < G.VexNum; ++v)
    {
        for (int w = 0; w < G.VexNum; ++w)
        {
            if ((G.arc[v][w] != 0) && visited[w] == 0)
            {
                cout << G.vex[w];
                visited[w] = 1;
            }
        }
    }
    //算法时间复杂度O(n^2)
}

我感觉这个写的就是逐个访问输出

不过也无所谓了,这玩意不是很重要,而且总归是能写的


http://www.niftyadmin.cn/n/206293.html

相关文章

C++运算符

C运算符 运算符是一种告诉编译器执行特定的数学或逻辑操作的符号。C 内置了丰富的运算符&#xff0c;并提供了以下类型的运算符&#xff1a; 算术运算符关系运算符逻辑运算符位运算符赋值运算符杂项运算符 1. 算术运算符 运算符描述实例把两个操作数相加A B 将得到 30-从第…

linux根目录结构

目录标题FHS目录结构特点目录类型路径以及工作目录1.路径2.工作目录FHS (filesystem hierarchy standard)文件系统层级标准&#xff0c;定义了在类unix系统中的目录结构歌目录内容&#xff0c;即让用户了解到已安装软件通常放置于哪个目录下。 目录结构特点 使用属性目录结构…

【牛客刷题专栏】0x18:JZ16 数值的整数次方(C语言编程题)

前言 个人推荐在牛客网刷题(点击可以跳转)&#xff0c;它登陆后会保存刷题记录进度&#xff0c;重新登录时写过的题目代码不会丢失。个人刷题练习系列专栏&#xff1a;个人CSDN牛客刷题专栏。 题目来自&#xff1a;牛客/题库 / 在线编程 / 剑指offer&#xff1a; 目录前言问题…

从零开始,国内实现调用GPT

前言&#xff1a; 这是一个简单的思路&#xff0c;部分参考来自GPT-4。 实际可以直接参考本人主页的另一篇 《宝塔快速反代openai官方的API接口&#xff0c;实现国内直接使用GPT》。 目录&#xff1a; 目录 一&#xff1a;获取API 二&#xff1a;网页制作 三&#xff1…

Python 小型项目大全 1~5

一、百吉饼 原文&#xff1a;http://inventwithpython.com/bigbookpython/project1.html 在百吉饼这种演绎逻辑游戏中&#xff0c;你必须根据线索猜出一个秘密的三位数。该游戏提供以下提示之一来响应您的猜测&#xff1a;"Pico"&#xff0c;当您的猜测在错误的位置有…

P1013 [NOIP1998 提高组] 进制位

题目描述 著名科学家卢斯为了检查学生对进位制的理解&#xff0c;他给出了如下的一张加法表&#xff0c;表中的字母代表数字。 例如&#xff1a; L K V E L L K V E K K V E KL V V E KL KK E E KL KK …

Linux-编译工具

一、gcc 1.1 一步到位 gcc 最简单的用法 gcc c_name.c # 会产生一个 a.out 的可执行文件这样会生成一个叫做 a.out 的可执行文件。 如果想要指定生成文件的名字&#xff0c;可以采用 -o 选项&#xff0c;也就是 output。比如下面的指令 gcc -o hello hello.c这个 -o …

分布式架构设计HDFS借鉴思考 GPT

分布式架构设计HDFS借鉴思考 HDFS&#xff08;Hadoop Distributed File System&#xff09;的主要设计思路 HDFS&#xff08;Hadoop Distributed File System&#xff09;的主要设计思路是将大数据文件划分成小的数据块&#xff0c;并存储在多个节点上&#xff0c;以实现数据的…