Bridges-C++  3.4.2
Bridges(C++ API)
GraphAdjMatrix.h
Go to the documentation of this file.
1 #ifndef GRAPH_ADJ_MATRIX_H
2 #define GRAPH_ADJ_MATRIX_H
3 
4 #include <stdexcept> //out of range
5 #include <sstream> //stringstream
6 
7 #include "Element.h" //DataStructure, unordered_map, string, cerr, using std
8 
9 namespace bridges {
10  namespace datastructure {
36  template <typename K, typename E1 = K, typename E2 = E1>
37  class GraphAdjMatrix : public DataStructure {
38  private:
39  unordered_map<K, Element<E1>* > vertices; // graph vertices
40  unordered_map<K, unordered_map<K, int> > matrix; // adjacency matrix
41  // maintain edge specific data
42  unordered_map<K, unordered_map<K, E2> > edge_data;
43 
44  public:
48  virtual const string getDStype() const override {
49  return "GraphAdjacencyMatrix";
50  }
51 
52  virtual ~GraphAdjMatrix() {
53  for (auto it : vertices)
54  delete it.second;
55  }
56  GraphAdjMatrix() = default;
57 
58  // The default version of these functions would be incorrect.
59  // So marking them delete to avoid problems.
60  // We could write them if necessary
61  GraphAdjMatrix(const GraphAdjMatrix&) = delete;
63 
64 
72  void addVertex(const K& k, const E1& e = E1()) {
73  stringstream conv;
74  conv << k; //Converts key into string
75  vertices[k] = new Element<E1>(e, conv.str());
76  for (const auto& p : vertices) {
77  // edge weights are 0
78  matrix[k][p.first] = matrix[p.first][k] = 0;
79  }
80  }
81 
92  void addEdge(const K& src, const K& dest, const unsigned int& wt) {
93  try { //create default link data
94  vertices.at(src)->links[vertices.at(dest)];
95  // add edge
96  matrix.at(src).at(dest) = wt;
97  }
98  catch (const out_of_range& ) {
99  cerr << "Cannot addEdge between non-existent verticies." << endl;
100  throw;
101  }
102  }
107  const unordered_map<K, unordered_map<K, int>>& getMatrix() const {
108  return matrix;
109  }
110 
120  const unordered_map<K, int>& getMatrix(K key) const {
121  return matrix.at(key);
122  }
123 
128  unordered_map<K, Element<E1> *>* getVertices() {
129  return &vertices;
130  }
135  const Element<E1>* getVertex(const K& key) const {
136  return vertices.at(key);
137  }
138 
144  Element<E1>* getVertex(const K& key) {
145  return vertices.at(key);
146  }
154  E1 getVertexData (const K& src) {
155  try {
156  Element<E1> *el = vertices.at(src);
157  return (vertices.at(src))->getValue();
158  }
159  catch ( const out_of_range& ) {
160  cerr << "getVertexData(): vertex not found" << endl;
161  throw;
162  }
163  // should never reach here
164  throw "getVertexData(): vertex not found";
165  }
172  void setVertexData (const K& vID, const E1& data) {
173  try {
174  Element<E1> *el = vertices.at(vID);
175  el->setValue (data);
176  }
177  catch ( const out_of_range& ) {
178  cerr << "setVertexData(): Nonexistent vertices or " <<
179  " edge not found" << endl;
180  throw;
181  }
182  catch (const char* msg) {
183  cerr << msg << endl;
184  }
185  }
194  E2 const & getEdgeData (const K& src, const K& dest) const {
195  try {
196  vertices.at(src);
197  vertices.at(dest);
198  return edge_data[src][dest];
199  }
200  catch ( const out_of_range& oor) {
201  cerr << "getEdgeData(): Nonexistent vertices or " <<
202  " edge not found" << endl;
203  throw;
204  }
205  catch (const char* msg) {
206  cerr << msg << endl;
207  throw;
208  }
209  // should never reach here
210  throw "getEdgeData(): Edge not found";
211  }
219  void setEdgeData (const K& src, const K& dest, const E2& data) {
220  try {
221  vertices.at(src);
222  vertices.at(dest);
223  edge_data[src][dest] = data;
224  }
225  catch ( const out_of_range& oor) {
226  cerr << "setEdgeData(): Nonexistent vertices or " <<
227  " edge not found" << endl;
228  throw;
229  }
230  catch (const char* msg) {
231  cerr << msg << endl;
232  throw;
233  }
234  }
244  try {
245  Element<E1> *el = vertices.at(k);
246 
247  return el->getVisualizer();
248  }
249  catch (const out_of_range& oor) {
250  cerr << "Graph vertex " << k << " not found in graph!" << endl;
251  throw;
252  }
253  }
263  LinkVisualizer *getLinkVisualizer (const K& k1, const K& k2) {
264  try {
265  Element<E1> *el1 = vertices.at(k1);
266  Element<E1> *el2 = vertices.at(k2);
267 
268  return el1->getLinkVisualizer(el2);
269  }
270  catch (const out_of_range& oor) {
271  cerr << "Either source or destination node not found in graph!"
272  << endl;
273  throw;
274  }
275  }
276 
277  private:
278 
284  virtual const string getDataStructureRepresentation() const override {
286 
287  // map the nodes to a sequence of ids, 0...N-1
288  // then get the JSON string for nodes placeholder
289  // nullptr prevents insertion of other nullptrs
290 
291  unordered_map<K, int> node_map;
292  int i = 0;
293  string nodes_JSON = "", links_JSON = "";
294 
295  for (const auto& v : this->vertices) {
296  if (node_map.emplace(v.first, i).second) {
297  i++;
298  nodes_JSON += v.second->getElementRepresentation() + COMMA;
299  }
300  }
301 
302  //Remove trailing comma and nullptr entry
303 
304  if (nodes_JSON.size()) {
305  nodes_JSON = nodes_JSON.erase(nodes_JSON.size() - 1);
306  }
307 
308  // iterate through the N squared entries vertices and form the links JSON
309 
310  for (const auto& src : vertices) {
311  for (const auto& dest : vertices) {
312  if (matrix.at(src.first).at(dest.first)) { // link exists
313  Element<E1>* src_v = vertices.at(src.first);
314  Element<E1>* dest_v = vertices.at(dest.first);
315  links_JSON += src_v->getLinkRepresentation(
316  *(src_v->getLinkVisualizer(dest_v)),
317  JSONencode(node_map.at(src.first)),
318  JSONencode(node_map.at(dest.first))) + COMMA;
319  }
320  }
321  }
322 
323  //Remove trailing comma
324  if (links_JSON.size()) {
325  links_JSON = links_JSON.erase(links_JSON.size() - 1);
326  }
327 
328  string graph_amatrix_json =
329  QUOTE + "nodes" + QUOTE + COLON +
330  OPEN_BOX + nodes_JSON + CLOSE_BOX + COMMA +
331  QUOTE + "links" + QUOTE + COLON + OPEN_BOX +
332  links_JSON + CLOSE_BOX +
333  CLOSE_CURLY;
334 
335  return graph_amatrix_json;
336  }
337  }; //end of GraphAdjList class
338  }
339 }//end of bridges namespace
340 #endif
This is the superclass of all data structure types in BRIDGES.
Definition: DataStructure.h:73
void setValue(const E &val)
Sets generic object to "val".
Definition: Element.h:229
LinkVisualizer * getLinkVisualizer(const Element *el)
Returns the LinkVisualizer of element.
Definition: Element.h:165
E const & getValue() const
Gets the object held in the generic object E.
Definition: Element.h:210
ElementVisualizer * getVisualizer()
Get the element visualizer object.
Definition: Element.h:144
This class maintains the visual properties of the a Bridges element.
Definition: ElementVisualizer.h:31
This class provides methods to represent adjacency matrix based graphs.
Definition: GraphAdjMatrix.h:37
GraphAdjMatrix(const GraphAdjMatrix &)=delete
const unordered_map< K, int > & getMatrix(K key) const
Definition: GraphAdjMatrix.h:120
E1 getVertexData(const K &src)
Definition: GraphAdjMatrix.h:154
virtual const string getDStype() const override
Definition: GraphAdjMatrix.h:48
const Element< E1 > * getVertex(const K &key) const
Definition: GraphAdjMatrix.h:135
Element< E1 > * getVertex(const K &key)
Definition: GraphAdjMatrix.h:144
unordered_map< K, Element< E1 > * > * getVertices()
Definition: GraphAdjMatrix.h:128
GraphAdjMatrix & operator=(const GraphAdjMatrix &)=delete
void setVertexData(const K &vID, const E1 &data)
Definition: GraphAdjMatrix.h:172
void setEdgeData(const K &src, const K &dest, const E2 &data)
Loads edge information.
Definition: GraphAdjMatrix.h:219
void addVertex(const K &k, const E1 &e=E1())
Definition: GraphAdjMatrix.h:72
const unordered_map< K, unordered_map< K, int > > & getMatrix() const
Definition: GraphAdjMatrix.h:107
void addEdge(const K &src, const K &dest, const unsigned int &wt)
Definition: GraphAdjMatrix.h:92
LinkVisualizer * getLinkVisualizer(const K &k1, const K &k2)
Definition: GraphAdjMatrix.h:263
E2 const & getEdgeData(const K &src, const K &dest) const
Definition: GraphAdjMatrix.h:194
ElementVisualizer * getVisualizer(const K &k)
Definition: GraphAdjMatrix.h:243
virtual ~GraphAdjMatrix()
Definition: GraphAdjMatrix.h:52
std::string JSONencode(const T &d)
Definition: JSONutil.h:37
these methods convert byte arrays in to base64 codes and are used in BRIDGES to represent the color a...
Definition: alltypes.h:4
const string COLON
Definition: DataStructure.h:51
const string OPEN_BOX
Definition: DataStructure.h:54
const string COMMA
Definition: DataStructure.h:50
const string CLOSE_BOX
Definition: DataStructure.h:55
const string CLOSE_CURLY
Definition: DataStructure.h:53
const string QUOTE
Definition: DataStructure.h:49