• 第七十五课 图的遍历(DFS)


    添加DFS函数:

      1 #ifndef GRAPH_H
      2 #define GRAPH_H
      3 
      4 #include "Object.h"
      5 #include "SharedPointer.h"
      6 #include "Array.h"
      7 #include "DynamicArray.h"
      8 #include "LinkQueue.h"
      9 #include "LinkStack.h"
     10 
     11 namespace DTLib
     12 {
     13 
     14 template < typename E >
     15 struct Edge : public Object
     16 {
     17     int b;
     18     int e;
     19     E data;
     20 
     21     Edge(int i=-1, int j=-1)
     22     {
     23         b = i;
     24         e = j;
     25     }
     26 
     27     Edge(int i, int j, const E& value)
     28     {
     29         b = i;
     30         e = j;
     31         data = value;
     32     }
     33 
     34     bool operator == (const Edge<E>& obj)
     35     {
     36         return (b == obj.b) && (e == obj.e);  //在这里不关注权值大小
     37     }
     38 
     39     bool operator != (const Edge<E>& obj)
     40     {
     41         return !(*this == obj);
     42     }
     43 };
     44 
     45 template < typename V, typename E >
     46 class Graph : public Object
     47 {
     48 protected:
     49     template < typename T >
     50     DynamicArray<T>* toArray(LinkQueue<T>& queue)
     51     {
     52         DynamicArray<T>* ret = new DynamicArray<T>(queue.length());
     53 
     54         if( ret != NULL )
     55         {
     56             for(int i=0; i<ret->length(); i++, queue.remove())
     57             {
     58                 ret->set(i, queue.front());
     59             }
     60         }
     61         else
     62         {
     63             THROW_EXCEPTION(NoEnoughMemoryException, "No memory to create ret object...");
     64         }
     65 
     66         return ret;
     67     }
     68 public:
     69     virtual V getVertex(int i) = 0;
     70     virtual bool getVertex(int i, V& value) = 0;
     71     virtual bool setVertex(int i, const V& value) = 0;
     72     virtual SharedPointer< Array<int> > getAdjacent(int i) = 0;
     73     virtual E getEdge(int i, int j) = 0;
     74     virtual bool getEdge(int i, int j, E& value) = 0;
     75     virtual bool setEdge(int i, int j, const E& value) = 0;
     76     virtual bool removeEdge(int i, int j) = 0;
     77     virtual int vCount() = 0;
     78     virtual int eCount() = 0;
     79     virtual int OD(int i) = 0;
     80     virtual int ID(int i) = 0;
     81     virtual int TD(int i)
     82     {
     83         return ID(i) + OD(i);
     84     }
     85 
     86     SharedPointer< Array<int> > BFS(int i)
     87     {
     88         DynamicArray<int>* ret = NULL;
     89 
     90         if( (0 <= i) && (i < vCount()) )
     91         {
     92             LinkQueue<int> q;
     93             LinkQueue<int> r;
     94             DynamicArray<bool> visited(vCount());
     95 
     96             for(int i=0; i<visited.length(); i++)
     97             {
     98                 visited[i] = false;
     99             }
    100 
    101             q.add(i);
    102 
    103             while( q.length() > 0 )
    104             {
    105                 int v = q.front();
    106 
    107                 q.remove();
    108 
    109                 if( !visited[v] )
    110                 {
    111                     SharedPointer< Array<int> > aj = getAdjacent(v);
    112 
    113                     for(int j=0; j<aj->length(); j++)
    114                     {
    115                         q.add((*aj)[j]);
    116                     }
    117 
    118                     r.add(v);
    119 
    120                     visited[v] = true;
    121                 }
    122             }
    123 
    124             ret = toArray(r);
    125         }
    126         else
    127         {
    128             THROW_EXCEPTION(InvalidParameterException, "Index i is invalid...");
    129         }
    130 
    131         return ret;
    132     }
    133 
    134     SharedPointer< Array<int> > DFS(int i)
    135     {
    136         DynamicArray<int>* ret = NULL;
    137 
    138         if( (0 <= i) && (i < vCount()) )
    139         {
    140             LinkStack<int> s;
    141             LinkQueue<int> r;
    142             DynamicArray<bool> visited(vCount());
    143 
    144             for(int j=0; j<visited.length(); j++)
    145             {
    146                 visited[j] = false;
    147             }
    148 
    149             s.push(i);
    150 
    151             while( s.size() > 0 )
    152             {
    153                 int v = s.top();
    154 
    155                 s.pop();
    156 
    157                 if( !visited[v] )
    158                 {
    159                     SharedPointer< Array<int> > aj = getAdjacent(v);
    160 
    161                     for(int j=aj->length() - 1; j>=0; j--)
    162                     {
    163                         s.push((*aj)[j]);
    164                     }
    165 
    166                     r.add(v);
    167 
    168                     visited[v] = true;
    169                 }
    170             }
    171 
    172             ret = toArray(r);
    173         }
    174         else
    175         {
    176             THROW_EXCEPTION(InvalidParameterException, "Index i is invalid...");
    177         }
    178 
    179         return ret;
    180     }
    181 };
    182 
    183 }
    184 
    185 #endif // GRAPH_H

    测试程序如下:

     1 #include <iostream>
     2 #include "BTreeNode.h"
     3 #include "ListGraph.h"
     4 #include "MatrixGraph.h"
     5 
     6 using namespace std;
     7 using namespace DTLib;
     8 
     9 
    10 int main()
    11 {
    12     MatrixGraph<9, char, int> g;
    13     const char* VD = "ABEDCGFHI";
    14 
    15     for(int i=0; i<9; i++)
    16     {
    17         g.setVertex(0, VD[i]);
    18     }
    19 
    20     g.setEdge(0, 1, 0);
    21     g.setEdge(1, 0, 0);
    22 
    23     g.setEdge(0, 3, 0);
    24     g.setEdge(3, 0, 0);
    25 
    26     g.setEdge(0, 4, 0);
    27     g.setEdge(4, 0, 0);
    28 
    29     g.setEdge(1, 2, 0);
    30     g.setEdge(2, 1, 0);
    31 
    32     g.setEdge(1, 4, 0);
    33     g.setEdge(4, 1, 0);
    34 
    35     g.setEdge(2, 5, 0);
    36     g.setEdge(5, 2, 0);
    37 
    38     g.setEdge(3, 6, 0);
    39     g.setEdge(6, 3, 0);
    40 
    41     g.setEdge(4, 6, 0);
    42     g.setEdge(6, 4, 0);
    43 
    44     g.setEdge(6, 7, 0);
    45     g.setEdge(7, 6, 0);
    46 
    47     g.setEdge(7, 8, 0);
    48     g.setEdge(8, 7, 0);
    49 
    50     SharedPointer< Array<int> > sa = g.DFS(0);
    51 
    52     for(int i=0; i<sa->length(); i++)
    53     {
    54         cout << (*sa)[i] << " ";
    55     }
    56 
    57     cout << endl;
    58 
    59     return 0;
    60 }

    结果如下:

     

    深度优先的思想就是二叉树的先序遍历思想。

    递归版的深入优先算法如下:

     1 #include <iostream>
     2 #include "BTreeNode.h"
     3 #include "ListGraph.h"
     4 #include "MatrixGraph.h"
     5 
     6 using namespace std;
     7 using namespace DTLib;
     8 
     9 template < typename V, typename E>
    10 void DFS(Graph<V, E>& g, int v, Array<bool>& visited)
    11 {
    12     if( (0 <= v) && (v < g.vCount()) )
    13     {
    14         cout << v << endl;
    15 
    16         visited[v] = true;
    17 
    18         SharedPointer< Array<int> > aj = g.getAdjacent(v);
    19 
    20         for(int i=0; i<aj->length(); i++)
    21         {
    22             if( !visited[(*aj)[i]] )
    23             {
    24                 DFS(g, (*aj)[i], visited);
    25             }
    26         }
    27     }
    28     else
    29     {
    30         THROW_EXCEPTION(InvalidParameterException, "Index v is invalid...");
    31     }
    32 }
    33 
    34 template < typename V, typename E >
    35 void DFS(Graph<V, E>& g, int v)
    36 {
    37     DynamicArray<bool> visited(g.vCount());
    38 
    39     for(int i=0; i<visited.length(); i++)
    40     {
    41         visited[i] = false;
    42     }
    43 
    44     DFS(g, v, visited);
    45 }
    46 
    47 int main()
    48 {
    49     MatrixGraph<9, char, int> g;
    50     const char* VD = "ABEDCGFHI";
    51 
    52     for(int i=0; i<9; i++)
    53     {
    54         g.setVertex(0, VD[i]);
    55     }
    56 
    57     g.setEdge(0, 1, 0);
    58     g.setEdge(1, 0, 0);
    59 
    60     g.setEdge(0, 3, 0);
    61     g.setEdge(3, 0, 0);
    62 
    63     g.setEdge(0, 4, 0);
    64     g.setEdge(4, 0, 0);
    65 
    66     g.setEdge(1, 2, 0);
    67     g.setEdge(2, 1, 0);
    68 
    69     g.setEdge(1, 4, 0);
    70     g.setEdge(4, 1, 0);
    71 
    72     g.setEdge(2, 5, 0);
    73     g.setEdge(5, 2, 0);
    74 
    75     g.setEdge(3, 6, 0);
    76     g.setEdge(6, 3, 0);
    77 
    78     g.setEdge(4, 6, 0);
    79     g.setEdge(6, 4, 0);
    80 
    81     g.setEdge(6, 7, 0);
    82     g.setEdge(7, 6, 0);
    83 
    84     g.setEdge(7, 8, 0);
    85     g.setEdge(8, 7, 0);
    86 
    87     SharedPointer< Array<int> > sa = g.DFS(0);
    88 
    89     for(int i=0; i<sa->length(); i++)
    90     {
    91         cout << (*sa)[i] << " ";
    92     }
    93 
    94     cout << endl;
    95 
    96     DFS(g, 0);
    97 
    98     return 0;
    99 }

    结果如下:

    小结:

  • 相关阅读:
    OSI Model Reference graphic / What do you guys think? Anything to edit/remove/add?
    Iframe Target for a Link
    Abp FullAuditedAggregateRoot
    After Effects上课视频
    Openwrt NAT ALG
    ipcalc.sh
    网络流量测试工具
    NatTypeTester
    基于DPDK开源项目
    GPS的调试与报文解析
  • 原文地址:https://www.cnblogs.com/wanmeishenghuo/p/9716219.html
Copyright © 2020-2023  润新知