Jafar
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines
Graphs.hpp
Go to the documentation of this file.
00001 
00014 #ifndef LGL_GRAPHS_HPP
00015 #define LGL_GRAPHS_HPP
00016 
00017 #include <map>
00018 #include <cmath>
00019 #include <vector>
00020 
00021 #include <boost/config.hpp>
00022 #include <boost/graph/adjacency_list.hpp>
00023 #include <boost/graph/iteration_macros.hpp>
00024 
00025 #include <lgl/Location.hpp>
00026 
00027 using namespace boost;
00028 
00029 namespace jafar {
00030   namespace lgl {
00031     
00036     template 
00037     <
00038       typename EDGE_BUNDLE,
00039       typename VERTEX_BUNDLE,
00040       typename EDGE_WEIGHT_T
00041       >   
00042     class NavGraphT {//{{{
00043       
00044     public :
00045       
00046       // declaration of the directed graph type
00047       typedef adjacency_list<
00048       listS,     // out edge container => make search algo faster
00049       vecS,      // vertex container
00050       directedS, //directed graph
00051       VERTEX_BUNDLE, 
00052       EDGE_BUNDLE
00053       > GraphContainer;
00054       
00055       /* a bunch of graph-specific typedefs */
00056       typedef typename graph_traits<GraphContainer>::vertex_descriptor Vertex;
00057       typedef typename graph_traits<GraphContainer>::edge_descriptor Edge;
00058       typedef std::pair<Edge, Edge> EdgePair;
00059       
00060       typedef typename graph_traits<GraphContainer>::vertex_iterator vertex_iterator;
00061       typedef typename graph_traits<GraphContainer>::edge_iterator edge_iterator;
00062       typedef typename graph_traits<GraphContainer>::adjacency_iterator adjacency_iterator;
00063       typedef typename graph_traits<GraphContainer>::out_edge_iterator out_edge_iterator;
00064       
00065       typedef typename graph_traits<GraphContainer>::degree_size_type degree_t;
00066       
00067       typedef std::pair<adjacency_iterator, adjacency_iterator> adjacency_vertex_range_t;
00068       typedef std::pair<out_edge_iterator, out_edge_iterator> out_edge_range_t;
00069       typedef std::pair<vertex_iterator, vertex_iterator> vertex_range_t;
00070       typedef std::pair<edge_iterator, edge_iterator> edge_range_t;
00071       
00072       // map between unique int key and vertex descriptor
00073       typedef std::map<int,Vertex> PosToVertex;
00074       // typename is here mandatory
00075       typedef typename std::map<int,Vertex>::iterator PosToVertex_iterator;
00076 
00077       // the weight map type on which searching algorithm is working
00078       typedef typename property_map<GraphContainer, EDGE_WEIGHT_T EDGE_BUNDLE::*>::type WeightMap;
00079       
00081       GraphContainer graph;
00082      
00083       PosToVertex verticesMap;
00084 
00085       int xsize, ysize;
00086 
00090       NavGraphT(int _xsize, int _ysize):
00091         xsize(_xsize),
00092         ysize(_ysize)
00093       {
00094       }
00095       
00096       ~NavGraphT() {}
00097 
00101       Vertex getVertex(const NavLocation& loc) {
00102         int posId = loc.pos_y * xsize + loc.pos_x;
00103         return verticesMap[posId];
00104       }
00105 
00110       bool getVertex(const NavLocation& loc, Vertex& v, bool check=false) {
00111         if (check==true) {
00112           if (!(vertexExists(loc)))
00113           {
00114             return false;
00115           }
00116         }
00117         v = getVertex(loc);
00118         return true;
00119       }
00120       
00122       NavLocation getClosestLocation(const NavLocation& _loc) {
00123         if (vertexExists(_loc))
00124         {
00125           return _loc;
00126         }
00127 
00128         NavLocation foundLoc(0,0);
00129         double dist = -1.0;
00130         double dist_tmp = -1.0;
00131         double xd = 0;
00132         double yd = 0;
00133         //Vertex v;
00134         BGL_FORALL_VERTICES(v,graph, adjacency_list<>) {
00135           xd = (double)(_loc.pos_x - ((graph)[v]).pos.pos_x);
00136           yd = (double)(_loc.pos_y - (graph)[v].pos.pos_y);
00137           dist_tmp = sqrt(xd*xd + yd*yd);
00138 
00139           // Getting closest location || init.
00140           if ( (dist_tmp < dist) || (dist < 0.0))
00141           {
00142             // Saving location
00143             foundLoc.setPos((graph)[v].pos.pos_x, (graph)[v].pos.pos_y);
00144             // Smallest distance
00145             dist = dist_tmp;
00146           }
00147         }
00148 
00149         return foundLoc;
00150       }
00151 
00153       Edge getEdge(const NavLocation& loc1,const NavLocation& loc2) {
00154         return edge(getVertex(loc1),getVertex(loc2),graph).first;
00155       }
00156       
00158       Edge getEdge(const NavLocation& loc1, const Vertex& vloc2) {
00159         return edge(getVertex(loc1), vloc2, graph).first;
00160       }
00161 
00163       Edge getEdge(const Vertex& vloc1,const NavLocation& loc2) {
00164         return edge(vloc1,getVertex(loc2),graph).first;
00165       }
00166 
00168       Edge getEdge(const Vertex& vloc1,  const Vertex& vloc2) {
00169         return edge(vloc1, vloc2, graph).first;
00170       }
00171       
00175       bool vertexExists(const NavLocation& loc) {
00176         int posId = loc.pos_y * xsize + loc.pos_x;
00177         PosToVertex_iterator it;
00178         it = verticesMap.find(posId);       
00179         if (it==verticesMap.end())
00180           return false;
00181         else
00182           return true;
00183       }
00184       
00188       Vertex addVertex(const NavLocation& loc) {
00189         int posId = loc.pos_y * xsize + loc.pos_x;
00190         if (vertexExists(posId))
00191         {
00192           return verticesMap[posId];
00193         } else {
00194           Vertex v = add_vertex(graph);
00195           verticesMap.insert(std::pair<int,Vertex>(posId,v));
00196           // temporary .. set the pos information of the graph vertex
00197           graph[v].pos = loc;
00198           return v;
00199         }
00200       }
00201       
00203       void removeGraphContent() { // DO NOT USE FOR NOW
00204         PosToVertex_iterator vi, next;
00205         vi = verticesMap.begin();
00206         for (next = vi; vi != verticesMap.end(); vi = next)
00207         {
00208           ++next;
00209           clear_vertex(vi->second, graph);
00210           remove_vertex(vi->second, graph);
00211         }
00212         verticesMap.clear();
00213       }
00214 
00216       bool removeVertex(const NavLocation& loc) {
00217         int posId = loc.pos_y * xsize + loc.pos_x;
00218         if (!vertexExists(posId))
00219           return true;
00220         else {
00221           Vertex v = verticesMap[posId];
00222           // delete in the graph container
00223           //  .. by firstly removing all in and out edges of v with clear_vertex() boost method
00224           clear_vertex(v,graph);
00225           remove_vertex(v,graph);
00226           // delete in the map
00227           verticesMap.erase(posId);
00228           return true;
00229         }
00230       }
00231 
00236       bool removeEdgesOnly(const NavLocation& loc) {
00237         int posId = loc.pos_y * xsize + loc.pos_x;
00238         if (!vertexExists(posId))
00239         {
00240           return false;
00241         }
00242         // else
00243         Vertex v = verticesMap[posId];
00244         // use clear_vertex of boost, this method clear all the edges connected to the given vertex 
00245         // but still let the vertex in the graph
00246         clear_vertex(v,graph);
00247         return true;        
00248       }
00249       
00254       bool removeOutEdges(const NavLocation& loc) {
00255         int posId = loc.pos_y * xsize + loc.pos_x;
00256         if (!vertexExists(posId))
00257         {
00258           return false;
00259         }
00260 
00261         // Removing out edges
00262         Vertex v = verticesMap[posId];
00263         out_edge_iterator oei, edge_end;
00264         tie(oei,edge_end) = out_edges(v,graph); 
00265         for (; oei != edge_end; ++oei) {
00266           // oei instead of *oei for speeding up the operation
00267           remove_edge(oei,graph);
00268         }
00269 
00270         return true;
00271       }
00272 
00277       bool removeInEdges(const NavLocation& loc) {
00278         int posId = loc.pos_y * xsize + loc.pos_x;
00279         if (!vertexExists(posId))
00280         {
00281           return false;
00282         }
00283 
00284         // Removing in-edges
00285         Vertex v = verticesMap[posId];
00286         adjacency_iterator ai, adj_end;
00287         tie(ai,adj_end) = adjacent_vertices(v,graph);
00288         for (; ai != adj_end; ++ai) {
00289           remove_edge(*ai,v,graph);
00290         }
00291         return true;
00292       }
00293 
00294       bool addEdge(const NavLocation& loc1, const NavLocation& loc2, bool check=false) {
00295         Vertex v1,v2;
00296         if (check) {
00297           v1 = addVertex(loc1);
00298           v2 = addVertex(loc2);
00299         } else {          
00300           v1 = getVertex(loc1);
00301           v2 = getVertex(loc2);
00302         }
00303 
00304         // Add edge to the graph
00305         add_edge(v1,v2,graph);
00306         
00307         // TODO: check if (true) the edge is newly added or (false) that it
00308         return true;
00309       }
00310 
00311       bool addEdge(const NavLocation& loc1, const NavLocation& loc2, Edge& edge, bool check=false) {
00312         Vertex v1,v2;
00313         if (check) {
00314           v1=addVertex(loc1);
00315           v2=addVertex(loc2);
00316         } else {          
00317           v1 = getVertex(loc1);
00318           v2 = getVertex(loc2);
00319         }
00320 
00321         // Save edge description
00322         edge = add_edge(v1,v2,graph).first;
00323         
00324         return true;
00325       }
00326       
00327       bool addEdge(const NavLocation& loc1, const NavLocation& loc2, const EDGE_BUNDLE& bundle, bool check=false) {
00328         Vertex v1,v2;
00329         if (check) {
00330           v1=addVertex(loc1);
00331           v2=addVertex(loc2);
00332         } else {          
00333           v1 = getVertex(loc1);
00334           v2 = getVertex(loc2);
00335         }
00336         Edge edge = add_edge(v1,v2,graph).first;
00337         
00338         setEdgeBundle(edge,bundle);
00339 
00340         return true;
00341       }
00342 
00346       bool addDualEdge(const NavLocation& loc1, const NavLocation& loc2)
00347       {
00348         // Creating vertices and checking if they don't already exist
00349         // anyway returning the corresponding vertex
00350         Vertex v1 = addVertex(loc1);
00351         Vertex v2 = addVertex(loc2);
00352         
00353         add_edge(v1,v2,graph);
00354         add_edge(v2,v1,graph);
00355 
00356         return true;
00357       }
00358 
00359       bool addDualEdgeFast(const NavLocation& loc1, const NavLocation& loc2)
00360       {
00361         
00362         Vertex v1 = getVertex(loc1);
00363         Vertex v2 = getVertex(loc2);
00364         
00365         add_edge(v1,v2,graph);
00366         add_edge(v2,v1,graph);
00367         
00368         return true;
00369       }
00370             
00371       bool addDualEdgeFast(const NavLocation& loc1, const NavLocation& loc2, const EDGE_BUNDLE& edge1, const EDGE_BUNDLE& edge2)
00372       {
00373         
00374         Vertex v1 = getVertex(loc1);
00375         Vertex v2 = getVertex(loc2);
00376         
00377         add_edge(v1,v2,graph);
00378         add_edge(v2,v1,graph);
00379         
00380         return true;
00381       }
00382 
00383 
00384       // add edges between all vertices
00385       bool mesh(std::vector<NavLocation>& locs) {
00386         int nbLocs = locs.size();
00387         int i,j;
00388         for (i=0;i<nbLocs;i++) {
00389           addVertex(locs[i]);
00390         }       
00391         for (i=0;i<nbLocs;i++) {
00392           for (j=i+1;j<nbLocs;j++) {
00393             addDualEdgeFast(locs[i],locs[j]);
00394           }
00395         }
00396         return true;
00397       }
00398 
00399       // add edges between all In Out locations
00400       // dont connect two postions with same x or same y
00401       bool connectInOutLocs(std::vector<NavLocation>& locs) {
00402         int nbLocs = locs.size();
00403         int i,j;
00404         for (i=0;i<nbLocs;i++) {
00405           addVertex(locs[i]);
00406         }       
00407         for (i=0;i<nbLocs;i++) {
00408           for (j=i+1;j<nbLocs;j++) {
00409             if ((locs[i].pos_x!=locs[j].pos_x)&&(locs[i].pos_y!=locs[j].pos_y))
00410               addDualEdgeFast(locs[i],locs[j]);
00411           }
00412         }
00413         return true;
00414       }
00415 
00416       // add edges between all vertices
00417       bool connect(NavLocation locToConnect, std::vector<NavLocation>& locs, bool verbose=false) {
00418         // Connecting it to its given neighborhood
00419         int nbLocs = locs.size();       
00420         for (int i=0;i<nbLocs;i++) {
00421           if (verbose)
00422           {
00423             std::cout << "# Connect " << locToConnect << " to " << locs[i] << std::endl;
00424           }
00425           // in the mean time adds mission locations
00426           addDualEdge(locToConnect,locs[i]);
00427         }       
00428         return true;
00429       }
00430 
00435       bool removeEdge(const NavLocation& loc1, const NavLocation& loc2) {
00436         if ((!vertexExists(loc1))||(!vertexExists(loc2)))
00437         {
00438           return false;
00439         }
00440 
00441         Vertex v1 = getVertex(loc1);
00442         Vertex v2 = getVertex(loc2);
00443 
00444         remove_edge(v1,v2,graph);
00445         return true;
00446       }
00447 
00448       bool removeDualEdge(const NavLocation& loc1, const NavLocation& loc2) {
00449         
00450         if ((!vertexExists(loc1))||(!vertexExists(loc2)))
00451         {
00452           return false;
00453         }
00454         
00455         Vertex v1 = getVertex(loc1);
00456         Vertex v2 = getVertex(loc2);
00457 
00458         remove_edge(v1,v2,graph);
00459         remove_edge(v2,v1,graph);
00460         return true;
00461       }
00462 
00466       bool setVertexBundle(const NavLocation& loc, const VERTEX_BUNDLE& bundle) {               
00467         
00468         Vertex v;
00469         if (!vertexExists(loc))
00470             v = addVertex(loc);
00471         else
00472           v = getVertex(loc);
00473         
00474         // set the bundle to the vertex
00475         get(vertex_bundle, graph)[v]=bundle;
00476         
00477         return true;
00478       }
00479 
00480       bool setEdgeBundle(const Edge& e, const EDGE_BUNDLE& bundle) {
00481         get(edge_bundle, graph)[e] = bundle;
00482         return true;
00483       }
00484 
00485       bool setEdgeBundle(const Vertex& v1, const Vertex& v2, const EDGE_BUNDLE& bundle) {
00486         get(edge_bundle, graph)[edge(v1,v2,graph).first]=bundle;
00487         return true;
00488       }
00489 
00490       bool setEdgeBundle(const NavLocation& loc1, const NavLocation& loc2, const EDGE_BUNDLE& bundle, bool check=false) {               
00491         if (check)
00492         {
00493           if ((!vertexExists(loc1)) || (!vertexExists(loc2)))
00494           {
00495             return false;
00496           }
00497         }
00498         Vertex v1 = getVertex(loc1);
00499         Vertex v2 = getVertex(loc2);
00500         
00501         get(edge_bundle, graph)[edge(v1,v2,graph).first]=bundle;
00502         
00503         return true;
00504       }
00505       
00506       bool getVertexBundle(const NavLocation& loc, VERTEX_BUNDLE& bundle, bool check=false) {       
00507         if (check)
00508           if (!vertexExists(loc))
00509             return false;
00510         Vertex v = getVertex(loc);
00511         
00512         // get the bundle from the vertex
00513         bundle = get(vertex_bundle, graph)[v];
00514         return true;
00515       }
00516 
00517       bool getVertexBundle(const Vertex& v, VERTEX_BUNDLE& bundle) {        
00518         // get the bundle from the vertex
00519         bundle = get(vertex_bundle, graph)[v];
00520         return true;
00521       }
00522 
00528       bool getEdgeBundle(const Edge& e, EDGE_BUNDLE& bundle) {//{{{
00529         bundle = get(edge_bundle, graph)[e];
00530         return true;
00531       }//}}}
00532 
00533       bool getEdgeBundle(const Vertex& v1, const Vertex& v2, EDGE_BUNDLE& bundle) {//{{{  
00534         bundle = get(edge_bundle, graph)[edge(v1,v2,graph).first];
00535         return true;
00536       }//}}}
00537       
00538       bool getEdgeBundle(const NavLocation& loc1, const NavLocation& loc2, EDGE_BUNDLE& bundle, bool check=false) {//{{{
00539         if (check)
00540         {
00541           if ((!vertexExists(loc1)) || (!vertexExists(loc2)))
00542           {
00543             return false;
00544           }
00545         }
00546         Vertex v1 = getVertex(loc1);
00547         Vertex v2 = getVertex(loc2);
00548         
00549         bundle = get(edge_bundle, graph)[edge(v1,v2,graph).first];
00550         return true;
00551       }//}}}
00552 
00554       GraphContainer* getGCtn() {
00555         return (&graph);
00556       }
00557       
00558       void clear() {
00559         graph.clear();
00560         verticesMap.clear();
00561       }
00562 
00563 
00564       /* operators */
00565       NavGraphT& operator=(const NavGraphT &rhs)
00566       {
00567         graph = rhs.graph;
00568         return *this;
00569       }
00570       
00574       void print() {
00575 
00576         vertex_iterator i, end;
00577         out_edge_iterator ei, edge_end;
00578         for(tie(i,end) = vertices(graph); i != end; ++i) {
00579           for (tie(ei,edge_end) = out_edges(*i, graph); ei != edge_end; ++ei) {
00580             std::cout << graph[*i].pos.pos_x <<":" << graph[*i].pos.pos_y; 
00581             std::cout << " --> ";
00582             std::cout << graph[target(*ei, graph)].pos.pos_x <<":" << graph[target(*ei, graph)].pos.pos_y;
00583             std::cout << std::endl;
00584           }
00585 
00586         }
00587       }
00588 
00589     private:
00590       
00591       bool vertexExists(const int& posId) {
00592         PosToVertex_iterator it;
00593         it = verticesMap.find(posId);       
00594         if (it==verticesMap.end())
00595           return false;
00596         else
00597           return true;
00598         return true;
00599       }
00600       
00601 
00602     };//}}}
00603 
00604   }
00605 
00606 }
00607 
00608 #endif // LGL_GRAPHS_HPP
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines

Generated on Wed Oct 15 2014 00:37:24 for Jafar by doxygen 1.7.6.1
LAAS-CNRS