00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
#ifndef LEMON_SMART_GRAPH_H
00018
#define LEMON_SMART_GRAPH_H
00019
00023
00024
#include <vector>
00025
#include <climits>
00026
00027
#include <lemon/invalid.h>
00028
00029
#include <lemon/array_map.h>
00030
#include <lemon/sym_map.h>
00031
00032
#include <lemon/map_registry.h>
00033
00034
#include <lemon/map_defines.h>
00035
00036
namespace lemon {
00037
00040
00041
00043
00059 class SmartGraph {
00060
00061
struct NodeT
00062 {
00063
int first_in,first_out;
00064 NodeT() : first_in(-1), first_out(-1) {}
00065 };
00066
struct EdgeT
00067 {
00068
int head, tail, next_in, next_out;
00069
00070 EdgeT() : next_in(-1), next_out(-1) {}
00071 };
00072
00073 std::vector<NodeT> nodes;
00074
00075 std::vector<EdgeT> edges;
00076
00077
00078
public:
00079
00080
typedef SmartGraph Graph;
00081
00082
class Node;
00083
class Edge;
00084
00085
class NodeIt;
00086
class EdgeIt;
00087
class OutEdgeIt;
00088
class InEdgeIt;
00089
00090
00091 CREATE_MAP_REGISTRIES;
00092
00093
CREATE_MAPS(
ArrayMap);
00094
00095
public:
00096
00097
SmartGraph() : nodes(), edges() { }
00098
SmartGraph(
const SmartGraph &_g) : nodes(_g.
nodes), edges(_g.
edges) { }
00099
00101 int nodeNum()
const {
return nodes.size(); }
00103 int edgeNum()
const {
return edges.size(); }
00104
00106
00109 int maxNodeId()
const {
return nodes.size()-1; }
00111
00114 int maxEdgeId()
const {
return edges.size()-1; }
00115
00116 Node tail(Edge e)
const {
return edges[e.n].tail; }
00117 Node head(Edge e)
const {
return edges[e.n].head; }
00118
00119 NodeIt& first(NodeIt& v)
const {
00120 v=NodeIt(*
this);
return v; }
00121 EdgeIt& first(EdgeIt& e)
const {
00122 e=EdgeIt(*
this);
return e; }
00123 OutEdgeIt& first(OutEdgeIt& e,
const Node v)
const {
00124 e=OutEdgeIt(*
this,v);
return e; }
00125 InEdgeIt& first(InEdgeIt& e,
const Node v)
const {
00126 e=InEdgeIt(*
this,v);
return e; }
00127
00129
00136 static int id(Node v) {
return v.n; }
00138
00145 static int id(Edge e) {
return e.n; }
00146
00147 Node addNode() {
00148 Node n; n.n=nodes.size();
00149 nodes.push_back(NodeT());
00150
00151
00152 node_maps.add(n);
00153
return n;
00154 }
00155
00156 Edge addEdge(Node u, Node v) {
00157 Edge e; e.n=edges.size(); edges.push_back(EdgeT());
00158 edges[e.n].tail=u.n; edges[e.n].head=v.n;
00159 edges[e.n].next_out=nodes[u.n].first_out;
00160 edges[e.n].next_in=nodes[v.n].first_in;
00161 nodes[u.n].first_out=nodes[v.n].first_in=e.n;
00162
00163 edge_maps.add(e);
00164
00165
return e;
00166 }
00167
00169
00176 Edge
findEdge(Node u,Node v, Edge prev = INVALID)
00177 {
00178
int e = (prev.n==-1)? nodes[u.n].first_out : edges[prev.n].next_out;
00179
while(e!=-1 && edges[e].tail!=v.n) e = edges[e].next_out;
00180 prev.n=e;
00181
return prev;
00182 }
00183
00184
void clear() {
00185 edge_maps.clear();
00186 edges.clear();
00187 node_maps.clear();
00188 nodes.clear();
00189 }
00190
00191
class Node {
00192
friend class SmartGraph;
00193
template <
typename T>
friend class NodeMap;
00194
00195
friend class Edge;
00196
friend class OutEdgeIt;
00197
friend class InEdgeIt;
00198
friend class SymEdge;
00199
00200
protected:
00201
int n;
00202
friend int SmartGraph::id(Node v);
00203 Node(
int nn) {n=nn;}
00204
public:
00205 Node() {}
00206 Node (Invalid) { n=-1; }
00207
bool operator==(
const Node i)
const {
return n==i.n;}
00208
bool operator!=(
const Node i)
const {
return n!=i.n;}
00209
bool operator<(
const Node i)
const {
return n<i.n;}
00210
00211
00212 };
00213
00214
class NodeIt :
public Node {
00215
const SmartGraph *G;
00216
friend class SmartGraph;
00217
public:
00218 NodeIt() : Node() { }
00219 NodeIt(
const SmartGraph& _G,Node n) : Node(n), G(&_G) { }
00220 NodeIt(Invalid i) : Node(i) { }
00221 NodeIt(
const SmartGraph& _G) : Node(_G.nodes.size()?0:-1), G(&_G) { }
00222 NodeIt &operator++() {
00223 n=(n+2)%(G->nodes.size()+1)-1;
00224
return *
this;
00225 }
00226
00227
00228 };
00229
00230
class Edge {
00231
friend class SmartGraph;
00232
template <
typename T>
friend class EdgeMap;
00233
00234
friend class SymSmartGraph;
00235
00236
friend class Node;
00237
friend class NodeIt;
00238
protected:
00239
int n;
00240
friend int SmartGraph::id(Edge e);
00241 Edge(
int nn) {n=nn;}
00242
public:
00244
00245 Edge() { }
00246 Edge (Invalid) { n=-1; }
00247
bool operator==(
const Edge i)
const {
return n==i.n;}
00248
bool operator!=(
const Edge i)
const {
return n!=i.n;}
00249
bool operator<(
const Edge i)
const {
return n<i.n;}
00250
00251
00252
00254
void setToId(
int id) { n=
id; }
00255 };
00256
00257
class EdgeIt :
public Edge {
00258
const SmartGraph *G;
00259
friend class SmartGraph;
00260
public:
00261 EdgeIt(
const SmartGraph& _G) : Edge(_G.edges.size()-1), G(&_G) { }
00262 EdgeIt(
const SmartGraph& _G, Edge e) : Edge(e), G(&_G) { }
00263 EdgeIt (Invalid i) : Edge(i) { }
00264 EdgeIt() : Edge() { }
00265 EdgeIt &operator++() { --n;
return *
this; }
00266
00267
00268 };
00269
00270
class OutEdgeIt :
public Edge {
00271
const SmartGraph *G;
00272
friend class SmartGraph;
00273
public:
00274 OutEdgeIt() : Edge() { }
00275 OutEdgeIt(
const SmartGraph& _G, Edge e) : Edge(e), G(&_G) { }
00276 OutEdgeIt (Invalid i) : Edge(i) { }
00277
00278 OutEdgeIt(
const SmartGraph& _G,
const Node v)
00279 : Edge(_G.nodes[v.n].first_out), G(&_G) {}
00280 OutEdgeIt &operator++() { n=G->edges[n].next_out;
return *
this; }
00281
00282
00283 };
00284
00285
class InEdgeIt :
public Edge {
00286
const SmartGraph *G;
00287
friend class SmartGraph;
00288
public:
00289 InEdgeIt() : Edge() { }
00290 InEdgeIt(
const SmartGraph& _G, Edge e) : Edge(e), G(&_G) { }
00291 InEdgeIt (Invalid i) : Edge(i) { }
00292 InEdgeIt(
const SmartGraph& _G,Node v)
00293 : Edge(_G.nodes[v.n].first_in), G(&_G) { }
00294 InEdgeIt &operator++() { n=G->edges[n].next_in;
return *
this; }
00295
00296
00297 };
00298
00299 };
00300
00302
00319
00320
00321 class SymSmartGraph :
public SmartGraph
00322 {
00323
public:
00324
typedef SymSmartGraph Graph;
00325
00326
00327 CREATE_SYM_EDGE_MAP_REGISTRY;
00328
00329
CREATE_SYM_EDGE_MAP(
ArrayMap);
00330
00331
00332
SymSmartGraph() :
SmartGraph() { }
00333
SymSmartGraph(
const SmartGraph &_g) :
SmartGraph(_g) { }
00335 Edge
addEdge(Node u, Node v)
00336 {
00337 Edge e = SmartGraph::addEdge(u,v);
00338 Edge f = SmartGraph::addEdge(v,u);
00339 sym_edge_maps.add(e);
00340 sym_edge_maps.add(f);
00341
return e;
00342 }
00343
00345
00348 static Edge
opposite(Edge e)
00349 {
00350 Edge f;
00351 f.n = e.n - 2*(e.n%2) + 1;
00352
return f;
00353 }
00354
00355
00356 };
00357
00359 }
00360
00361
00362
00363
00364
#endif //LEMON_SMART_GRAPH_H