• 第六章小结


    第六章主要学习了图的两种存储结构---邻接矩阵表示法和邻接表表示法,以及基于两种存储结构对图的遍历---深度优先遍历和广度优先遍历

    PTA作业:

    给定一个有N个顶点和E条边的无向图,请用DFS和BFS分别列出其所有的连通集。假设顶点从0到N−1编号。进行搜索时,假设我们总是从编号最小的顶点出发,按编号递增的顺序访问邻接点。

    输入格式:

    输入第1行给出2个整数N(0<N≤10)和E,分别是图的顶点数和边数。随后E行,每行给出一条边的两个端点。每行中的数字之间用1空格分隔。

    输出格式:

    按照"{ v​1​​ v​2​​ ... vk​​ }"的格式,每行输出一个连通集。先输出DFS的结果,再输出BFS的结果。

     sample

    输入

    8 6

    0 7

    0 1

    2 0

    4 1

    2 4

    3 5

    输出

    { 0 1 4 2 7 }

    { 3 5 }

    { 6 }

    { 0 1 2 7 4 }

    { 3 5 }

    { 6 }

    采用邻接矩阵存储结构解决这个问题

    #include <iostream>
    #include <queue>//队列
    using namespace std;
    #define MNum 10
    #define OK 1
    typedef int Status; 
    View Code
    typedef struct
    {//定义邻接矩阵 
        int vexs[MNum];//顶点表 
        int arc[MNum][MNum];//邻接矩阵 
        int vexnum,arcnum;//顶点数,边数 
    }Graph;
    View Code定义邻接矩阵
    Status create(Graph &g);
    void DFS(Graph &g,int v);
    void BFS(Graph &g,int v);
    View Code函数声明

    定义全局变量visit数组,用来判断顶点是否被访问

    bool visit[MNum];
    View Code数组初始化为false
    int main()
    {
        Graph g;
        create(g);
        
        for(int i=0;i<g.vexnum;i++)
        {
            if(!visit[i])
            {
             visit[i]=true;
             cout<<"{"<<" ";
             DFS(g,i);
             cout<<"}"<<endl;
            }
        }
        //将visit数组重新置为false 
        for(int i=0;i<g.vexnum;++i)
           visit[i]={false};
           
        for(int i=0;i<g.vexnum;i++)
        { //若顶点未访问,先visit数组置true,递归BFS 
            if(!visit[i])
            {
             visit[i]=true;
             cout<<"{"<<" ";
             BFS(g,i);
             cout<<"}"<<endl;
            }
        }
        return 0;
    }
    View Code主函数

    主函数中先进了DFS,visit数组已经全部置为true,所以在进行BFS时须再次将visit数组置为false,这样BFS才能继续进行,否则不会输出广度优先遍历下图的连通分量集合(我就是在这入坑了)。

    Status create(Graph &g)
    {
        int v1,v2;
        int n,i,j,k;
        
        cin>>g.vexnum>>g.arcnum;//输入顶点数,边数 
        for(n=0;i<g.vexnum;++i)
          g.vexs[i]=i;//顶点即数组下标 
          
        for(i=0;i<g.vexnum;++i)
          for(j=0;j<g.vexnum;++j)
              g.arc[i][j]=0;//初始化邻接矩阵为0 
              
        for(k=0;k<g.arcnum;++k)
        {//两顶点有边即以两顶点为下标的元素置1 
            cin>>v1>>v2;//输入顶点下标
            g.arc[v1][v2]=1;
            g.arc[v2][v1]=g.arc[v1][v2];//无向图的对称性 
        }
        return OK;
     } 
    View Code//邻接矩阵表示图
    void DFS(Graph &g,int v)
    {//从v顶点开始的深度优先遍历 
        cout<<v<<" "; 
        for(int w=0;w<g.vexnum;++w)
          {
           if((g.arc[v][w]!=0)&&(!visit[w]))
           {//如果边存在,顶点未访问,递归调用DFS 
               visit[w]=true;
            DFS(g,w);
           }
          }
    }
    View Code//DFS
    void BFS(Graph &g,int v)
    {//从顶点v开始广度优先遍历 
        queue <int> q;
        int u;
        q.push(v);//初始顶点入栈 
        while(!q.empty())
        {
            u=q.front();
            cout<<u<<" ";//输出对头
            q.pop();
            for(int i=0;i<g.vexnum;i++)
            {//两顶点边存在且顶点未被访问,该顶点对于应的visit数组置true,将顶点入队 
                if((g.arc[u][i]!=0)&&(!visit[i]))
                {
                    visit[i]=true;
                    q.push(i);
                }
            }
         }  
    }
    View Code//BFS

    PTA提交作业在格式上有很大的要求;无法输出广度优先遍历的连通分量集合,就在BFS函数里加上一些输出语句,查看在程序在哪里中断,在哪运行条件不符合,可以比较有效的找到漏洞。

  • 相关阅读:
    工作实战之项目常用技术
    Thymeleaf的错误解决方式
    实用小demo
    idea常用的几个插件
    idea2019+Plugins中搜索不到任何插件解决办法
    git的初体验
    springboot2.+的整合log4j2错误解决浅谈
    MobaXterm百度网盘下载
    阿里云RDS云数据库连接步骤
    读源码学编程之——死循环妙用
  • 原文地址:https://www.cnblogs.com/liuyuany/p/10886632.html
Copyright © 2020-2023  润新知