【图的实现】“广度优先搜索遍历”以及“深度优先搜索遍历”必会

/*
  图的存储与图的遍历
*/

/*

      A
    /   \
   B     D
  /\     /\
  C F    G H
  \/
  E
  A B C D E F G H
A 0 1 0 1 0 0 0 0
B 1 0 1 0 0 1 0 0
C     0 0 1 0 0 0
D       0 0 0 1 1
E
F
G
H

实现这样一个图,用广度优先搜索和深度优先分别遍历

图类的基本数据有:
int m_iCapacity;//图中最多可以容纳的顶点数
int m_iNodeCount;//已经添加的定点(结点)个数
Node *m_pNodeArray;//用来存放顶点数组
int *m_pMatrix;//用来存放邻接矩阵

顶点(结点)基本数据有:
char m_cData;
bool m_bIsVisited;

头文件:

#include<vector>
using namespace std;
#include"Node.h"
#include<iostream>
class CMap
{
public:
    CMap(int capacity);
    ~CMap();
    bool addNode(Node*pNode);                                               //向图中加入定点(结点)
    void resetNode();                                                       //重置顶点
    bool setValueToMatrixForDirectedGraph(int row, int col, int val = 1);   //为有向图设置邻接矩阵,val默认为1
    bool setValueToMatrixForUndirectedGraph(int row, int col, int val = 1);//为无向图设置邻接矩阵

    void printMatrix();                                                     //打印邻接矩阵

    void depthFirstTraverse(int nodeIndex);                                 //深度优先遍历
    void breadthFirstTraverse(int nodeIndex);                               //广度优先遍历

private:
    bool getValueFromMatrix(int row, int col, int &val);                   //从矩阵中获取权值
    void breadthFirstTraverseImpl(vector<int>preVec);                          //广度优先遍历实现函数
private:
    int m_iCapacity;//图中最多可以容纳的顶点数
    int m_iNodeCount;//已经添加的定点(结点)个数
    Node *m_pNodeArray;//用来存放顶点数组
    int *m_pMatrix;//用来存放邻接矩阵

};
#ifndef NODE_H
#define NODE_H

class Node {
public:
    Node(char data = 0); 
    char m_cData;
    bool m_bIsVisited;
};


#endif

类成员函数的实现:

#include"CMap.h"
CMap::CMap(int capacity)
{
    m_iCapacity = capacity;
    m_iNodeCount = 0;
    m_pNodeArray = new Node[m_iCapacity];
    m_pMatrix = new int[m_iCapacity*m_iCapacity];
    memset(m_pMatrix, 0, m_iCapacity*m_iCapacity*sizeof(int));//对邻接矩阵进行初始化

}

CMap::~CMap()
{
    delete[]m_pNodeArray;
    delete[]m_pMatrix;

}
bool CMap::addNode(Node *pNode)
{

    if (pNode == NULL)
    {
        return false;
    }
    m_pNodeArray[m_iNodeCount].m_cData = pNode->m_cData;
    m_iNodeCount++;
    return true;

}

void CMap::resetNode()
{
    for (int i = 0; i < m_iNodeCount; i++)
    {
        m_pNodeArray[i].m_bIsVisited = false;
    }
}
//有向图
bool CMap::setValueToMatrixForDirectedGraph(int row,int col, int val)
{
    if (row < 0 || row >= m_iCapacity)
    {
        return false;
    }
    if (col < 0 || col >= m_iCapacity)
    {
        return false;
    }
    m_pMatrix[row*m_iCapacity + col] = val;
    return true;

}

//无向图
bool CMap::setValueToMatrixForUndirectedGraph(int row, int col, int val)
{
    if (row < 0 || row >= m_iCapacity)
    {
        return false;
    }
    if (col < 0 || col >= m_iCapacity)
    {
        return false;
    }
    m_pMatrix[row*m_iCapacity + col] = val;
    m_pMatrix[col*m_iCapacity + row] = val;//对角线相应的位置
    return true;
}

bool CMap::getValueFromMatrix(int row, int col, int &val)
{
    val = m_pMatrix[row*m_iCapacity + col];
    return true;
}

void CMap::printMatrix()
{
    for (int i = 0; i < m_iCapacity; i++)
    {
        for (int k = 0; k < m_iCapacity; k++)
        {
            cout << m_pMatrix[i*m_iCapacity + k] << " ";
        }
        cout << endl;
    }
}

//深度优先搜索
void CMap::depthFirstTraverse(int nodeIndex)
{
    int value = 0;

    cout << m_pNodeArray[nodeIndex].m_cData << " ";
    m_pNodeArray[nodeIndex].m_bIsVisited = true;

    //通过邻接矩阵判断是否与其他的定点有连接
    for (int i = 0; i < m_iCapacity; i++)
    {
        getValueFromMatrix(nodeIndex, i, value);
        if (value !=0)//再判断有弧连接其他顶点
        {
            //再判断该节点是否被访问过
            if (m_pNodeArray[i].m_bIsVisited)
            {
                continue;
            }
            else
            {
                depthFirstTraverse(i);
            }
        }
        else //如果没有去向索引为i顶点的弧,则循环继续
        {
            continue;
        }

    }

}

//广度优先搜索
void CMap::breadthFirstTraverse(int nodeIndex)
{
    cout << m_pNodeArray[nodeIndex].m_cData << " ";
    m_pNodeArray[nodeIndex].m_bIsVisited = true;

    vector<int>curVec;
    curVec.push_back(nodeIndex);

    breadthFirstTraverseImpl(curVec);

}

void CMap::breadthFirstTraverseImpl(vector<int>preVec)
{
    int value = 0;
    vector<int>curVec;
    for (int j = 0; j <(int) preVec.size(); j++)
    {
        for (int i = 0; i < m_iCapacity; i++)
        {
            getValueFromMatrix(preVec[j], i, value);
            if (value != 0)
            {
                if (m_pNodeArray[i].m_bIsVisited)
                {
                    continue;
                }
                else
                {
                    cout << m_pNodeArray[i].m_cData << " ";
                    m_pNodeArray[i].m_bIsVisited = true;


                    curVec.push_back(i);

                }
            }
            else
            {
                continue;
            }
        }
    }

    if (curVec.size() == 0)
    {
        return ;
    }
    else
    {
        breadthFirstTraverseImpl(curVec);
    }

}

#include"Node.h"

Node::Node(char data)
{
    m_cData = data;
    m_bIsVisited = false;
}

测试程序:

#include<iostream>
#include<stdlib.h>

#include"CMap.h"
using namespace std;
int main(void)
{
    CMap*pMap = new CMap(8);

    Node *pNodeA = new Node('A');
    Node *pNodeB = new Node('B');
    Node *pNodeC = new Node('C');
    Node *pNodeD= new Node('D');
    Node *pNodeE = new Node('E');
    Node *pNodeF = new Node('F');
    Node *pNodeG = new Node('G');
    Node *pNodeH= new Node('H');


    pMap->addNode(pNodeA);
    pMap->addNode(pNodeB);
    pMap->addNode(pNodeC);
    pMap->addNode(pNodeD);
    pMap->addNode(pNodeE);
    pMap->addNode(pNodeF);
    pMap->addNode(pNodeG);
    pMap->addNode(pNodeH);


    pMap->setValueToMatrixForUndirectedGraph(0, 1);
    pMap->setValueToMatrixForUndirectedGraph(0, 3);
    pMap->setValueToMatrixForUndirectedGraph(1, 2);
    pMap->setValueToMatrixForUndirectedGraph(1, 5);
    pMap->setValueToMatrixForUndirectedGraph(3, 6);
    pMap->setValueToMatrixForUndirectedGraph(3, 7);
    pMap->setValueToMatrixForUndirectedGraph(6, 7);
    pMap->setValueToMatrixForUndirectedGraph(2, 4);
    pMap->setValueToMatrixForUndirectedGraph(4, 5);


    pMap->printMatrix();
    cout << endl;

    pMap->resetNode();
    pMap->depthFirstTraverse(0);
    cout << endl;

    pMap->resetNode();
    pMap->breadthFirstTraverse(0);
    cout <<endl;

    system("pause");
    return 0;
}

《【图的实现】“广度优先搜索遍历”以及“深度优先搜索遍历”必会》

    原文作者:数据结构之图
    原文地址: https://blog.csdn.net/lizhidefengzi/article/details/54708151
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞