igraph.h
1 /*
2  @copyright Russell Standish 2000-2013
3  @author Russell Standish
4  This file is part of EcoLab
5 
6  Open source licensed under the MIT license. See LICENSE for details.
7 */
8 
13 #ifndef ECOLAB_IGRAPH_H
14 #define ECOLAB_IGRAPH_H
15 #include "graph.h"
16 #include "igraph/igraph.h"
17 
18 
19 // TODO fix up error handling
20 namespace ecolab
21 {
22  struct IGraphError: public std::exception
23  {
24  int err;
25  IGraphError(int err): err(err) {}
26  const char* what() const throw()
27  {return igraph_strerror(err);}
28  };
29 
30  class IGraph: public igraph_t
31  {
32  static int errorhandler;
33  void addEdges(const Graph& g);
34  public:
36  IGraph(unsigned nodes=0, bool directed=false)
37  {igraph_empty(this, nodes, directed);}
38  IGraph(const IGraph& x) {igraph_copy(this,&x);}
39  IGraph(const Graph& x) {
40  igraph_empty(this, x.nodes(), x.directed());
41  addEdges(x);
42  }
43  ~IGraph() {
44  ++errorhandler; //does nothing other than ensure linkage
45  try {igraph_destroy(this);}
46  catch (std::exception& ex) {
47  std::cerr << "unexpected exception encountered: "<<
48  ex.what()<<std::endl;
49  }
50  }
51 
52 
53  const IGraph& operator=(const IGraph& x)
54  {igraph_copy(this,&x); return *this;}
55  const IGraph& operator=(const Graph& x) {
56  clear(x.nodes());
57  addEdges(x);
58  return *this;
59  }
60 
62  {
63  const igraph_t* g;
64  igraph_eit_t it;
65  mutable Edge edge;
66  public:
67  const_iterator(const igraph_t& graph, const igraph_es_t& es):
68  g(&graph) {igraph_eit_create(g,es,&it);}
69  ~const_iterator() {igraph_eit_destroy(&it);}
70  bool operator==(const const_iterator& x) const {
71  // return true if both iterators are end, otherwise if they're equal
72  return (g==x.g &&
73  IGRAPH_EIT_END(it) && IGRAPH_EIT_END(x.it)) ||
74  (!IGRAPH_EIT_END(it) && !IGRAPH_EIT_END(x.it) && operator*()==*x);
75  }
76  bool operator!=(const const_iterator& x) const {return !operator==(x);}
77  Edge operator*() const {
78  igraph_integer_t from, to;
79  igraph_edge(g, IGRAPH_EIT_GET(it), &from, &to);
80  Edge e(from,to);
81  return e;
82  }
83  const Edge* operator->() const {
84  edge=operator*();
85  return &edge;
86  }
87  const_iterator& operator++() {
88  IGRAPH_EIT_NEXT(it);
89  return *this;
90  }
91  };
92 
93  const_iterator begin() const
94  {
95  igraph_es_t es;
96  igraph_es_all(&es,IGRAPH_EDGEORDER_ID); //select all edges
97  return const_iterator(*this,es);
98  }
99 
100 
101  const_iterator end() const
102  {
103  igraph_es_t es;
104  igraph_es_none(&es); //select no edges
105  return const_iterator(*this,es);
106  }
107 
108  unsigned nodes() const {return igraph_vcount(this);}
109  unsigned links() const {return igraph_ecount(this);}
110  void push_back(const Edge& e)
111  {
112  unsigned n=nodes(), maxN=std::max(e.source(), e.target())+1;
113  if (n<maxN) igraph_add_vertices(this,maxN-n,0); //ensure enough nodes
114  igraph_add_edge(this, e.source(), e.target());
115  }
116 
117  bool contains(const Edge& e) const {
118  igraph_integer_t eid;
119 #ifdef IGRAPH_VERSION
120  return igraph_get_eid(this,&eid,e.source(),e.target(),true,true)==0;
121 #else
122  try {
123  igraph_get_eid(this,&eid,e.source(),e.target(),true);
124  return true; // edge exists if eid found
125  }
126  catch (std::exception) {return false;}
127 #endif
128  }
129 
130  bool directed() const {return igraph_is_directed(this);}
131 
132  void clear(unsigned nodes=0) {
133  bool dir=directed();
134  igraph_destroy(this);
135  igraph_empty(this,nodes,dir);
136  }
137  };
138 
139 }
140 #endif
virtual unsigned nodes() const =0
number of nodes
virtual bool directed() const =0
true if a bidirectional graph (all edges go both ways)
Definition: igraph.h:22
Definition: graph.h:94
Definition: igraph.h:61
EcoLab graph library.
Definition: igraph.h:30
IGraph(unsigned nodes=0, bool directed=false)
construct an iGraph with nodes, directed or not
Definition: igraph.h:36
_OPENMP
Definition: accessor.h:16
Definition: graph.h:45