[Lemon-commits] [lemon_svn] deba: r2199 - in hugo/trunk: demo lemon test

Lemon SVN svn at lemon.cs.elte.hu
Mon Nov 6 20:50:52 CET 2006


Author: deba
Date: Mon Sep 12 11:19:52 2005
New Revision: 2199

Added:
   hugo/trunk/demo/grid_graph_demo.cc
Modified:
   hugo/trunk/demo/Makefile.am
   hugo/trunk/lemon/grid_graph.h
   hugo/trunk/test/undir_graph_test.cc

Log:
Fixing and improving GridGraph
 


Modified: hugo/trunk/demo/Makefile.am
==============================================================================
--- hugo/trunk/demo/Makefile.am	(original)
+++ hugo/trunk/demo/Makefile.am	Mon Sep 12 11:19:52 2005
@@ -14,7 +14,8 @@
 	hello_lemon \
 	sub_graph_adaptor_demo \
 	descriptor_map_demo \
-	coloring
+	coloring \
+	grid_graph_demo
 
 if HAVE_GLPK
 noinst_PROGRAMS += lp_demo lp_maxflow_demo
@@ -37,6 +38,8 @@
 
 graph_to_eps_demo_SOURCES = graph_to_eps_demo.cc
 
+grid_graph_demo_SOURCES = grid_graph_demo.cc
+
 graph_orientation_SOURCES = graph_orientation.cc
 
 min_route_SOURCES = min_route.cc

Added: hugo/trunk/demo/grid_graph_demo.cc
==============================================================================
--- (empty file)
+++ hugo/trunk/demo/grid_graph_demo.cc	Mon Sep 12 11:19:52 2005
@@ -0,0 +1,29 @@
+#include <lemon/grid_graph.h>
+#include <lemon/graph_adaptor.h>
+#include <lemon/graph_to_eps.h>
+#include <lemon/xy.h>
+
+#include <iostream>
+#include <fstream>
+
+using namespace lemon;
+using namespace std;
+
+int main() {
+  GridGraph graph(5, 7);
+  GridGraph::NodeMap<xy<double> > coord(graph);
+  for (int i = 0; i < graph.width(); ++i) {
+    for (int j = 0; j < graph.height(); ++j) {
+      coord[graph(i, j)] = xy<double>(i * 10.0, j * 10.0);
+    }
+  }
+  graphToEps(graph, "grid_graph.eps").scaleToA4().
+    title("Grid graph").
+    copyright("(C) 2005 LEMON Project").
+    coords(coord).
+    enableParallel().
+    nodeScale(.45).
+    drawArrows().
+    run();
+  return 0;
+}

Modified: hugo/trunk/lemon/grid_graph.h
==============================================================================
--- hugo/trunk/lemon/grid_graph.h	(original)
+++ hugo/trunk/lemon/grid_graph.h	Mon Sep 12 11:19:52 2005
@@ -47,19 +47,68 @@
     /// \brief Creates a grid graph with the given size.
     ///
     /// Creates a grid graph with the given size.
-    void construct(int height, int width) {
+    void construct(int width, int height) {
       _height = height; _width = width;
       _nodeNum = height * width; _edgeNum = 2 * _nodeNum - width - height;
       _edgeLimit = _nodeNum - width;
     }
 
+    /// \brief Gives back the edge goes down from the node.
+    ///
+    /// Gives back the edge goes down from the node. If there is not
+    /// outgoing edge then it gives back INVALID.
+    Edge _down(Node n) const {
+      if (n.id < _nodeNum - _width) {
+	return Edge(n.id);
+      } else {
+	return INVALID;
+      }
+    }
+
+    /// \brief Gives back the edge comes from up into the node.
+    ///
+    /// Gives back the edge comes from up into the node. If there is not
+    /// incoming edge then it gives back INVALID.
+    Edge _up(Node n) const {
+      if (n.id >= _width) {
+	return Edge(n.id - _width);
+      } else {
+	return INVALID;
+      }
+    }
+
+    /// \brief Gives back the edge goes right from the node.
+    ///
+    /// Gives back the edge goes right from the node. If there is not
+    /// outgoing edge then it gives back INVALID.
+    Edge _right(Node n) const {
+      if (n.id % _width < _width - 1) {
+	return _edgeLimit + n.id % _width + (n.id / _width) * (_width - 1);
+      } else {
+	return INVALID;
+      }
+    }
+
+    /// \brief Gives back the edge comes from left into the node.
+    ///
+    /// Gives back the edge comes left up into the node. If there is not
+    /// incoming edge then it gives back INVALID.
+    Edge _left(Node n) const {
+      if (n.id % _width > 0) {
+	return _edgeLimit + n.id % _width + (n.id / _width) * (_width - 1) - 1;
+      } else {
+	return INVALID;
+      }
+    }
+
+
   public:
     
     /// \brief The node on the given position.
     /// 
     /// Gives back the node on the given position.
     Node operator()(int i, int j) const {
-      return Node(i * _width + j);
+      return Node(i + j * _width);
     }
 
     /// \brief Gives back the row index of the node.
@@ -72,7 +121,7 @@
     /// \brief Gives back the coloumn index of the node.
     ///
     /// Gives back the coloumn index of the node.
-    int col(Node node) const {
+    int col(Node n) const {
       return n.id % _width;    
     }
 
@@ -277,14 +326,10 @@
   };
 
 
-  typedef UndirGraphExtender<GridGraphBase>
-  UndirGridGraphBase;
-  typedef AlterableUndirGraphExtender<UndirGridGraphBase> 
-  AlterableGridGraphBase;
-  typedef IterableUndirGraphExtender<AlterableGridGraphBase> 
-  IterableGridGraphBase;
-  typedef MappableUndirGraphExtender<IterableGridGraphBase> 
-  MappableGridGraphBase;
+  typedef MappableUndirGraphExtender<
+    IterableUndirGraphExtender<
+    AlterableUndirGraphExtender<
+    UndirGraphExtender<GridGraphBase> > > > ExtendedGridGraphBase;
 
   /// \ingroup graphs
   ///
@@ -311,10 +356,47 @@
   /// "Undirected Graph" concept.
   ///
   /// \author Balazs Dezso
-  class GridGraph : public MappableGridGraphBase {
+  class GridGraph : public ExtendedGridGraphBase {
   public:
     
-    GridGraph(int m, int n) { construct(m, n); }
+    GridGraph(int n, int m) { construct(n, m); }
+    
+    /// \brief Gives back the edge goes down from the node.
+    ///
+    /// Gives back the edge goes down from the node. If there is not
+    /// outgoing edge then it gives back INVALID.
+    Edge down(Node n) const {
+      UndirEdge ue = _down(n);
+      return ue != INVALID ? direct(ue, true) : INVALID;
+    }
+    
+    /// \brief Gives back the edge goes up from the node.
+    ///
+    /// Gives back the edge goes up from the node. If there is not
+    /// outgoing edge then it gives back INVALID.
+    Edge up(Node n) const {
+      UndirEdge ue = _up(n);
+      return ue != INVALID ? direct(ue, false) : INVALID;
+    }
+
+    /// \brief Gives back the edge goes right from the node.
+    ///
+    /// Gives back the edge goes right from the node. If there is not
+    /// outgoing edge then it gives back INVALID.
+    Edge right(Node n) const {
+      UndirEdge ue = _right(n);
+      return ue != INVALID ? direct(ue, true) : INVALID;
+    }
+
+    /// \brief Gives back the edge goes left from the node.
+    ///
+    /// Gives back the edge goes left from the node. If there is not
+    /// outgoing edge then it gives back INVALID.
+    Edge left(Node n) const {
+      UndirEdge ue = _left(n);
+      return ue != INVALID ? direct(ue, false) : INVALID;
+    }
+    
   };
 }
 #endif

Modified: hugo/trunk/test/undir_graph_test.cc
==============================================================================
--- hugo/trunk/test/undir_graph_test.cc	(original)
+++ hugo/trunk/test/undir_graph_test.cc	Mon Sep 12 11:19:52 2005
@@ -5,6 +5,7 @@
 #include <lemon/list_graph.h>
 #include <lemon/smart_graph.h>
 #include <lemon/full_graph.h>
+#include <lemon/grid_graph.h>
 
 #include <lemon/graph_utils.h>
 
@@ -43,12 +44,35 @@
   checkConcept<UndirGraph, UndirFullGraph>();
 
   checkConcept<UndirGraph, UndirGraph>();
+
+  checkConcept<UndirGraph, GridGraph>();
 }
 
 template <typename Graph>
 void check_item_counts(Graph &g, int n, int e) {
-  check(countNodes(g)==n, "Wrong node number.");
-  check(countEdges(g)==2*e, "Wrong edge number.");
+  int nn = 0;
+  for (typename Graph::NodeIt it(g); it != INVALID; ++it) {
+    ++nn;
+  }
+
+  check(nn == n, "Wrong node number.");
+  check(countNodes(g) == n, "Wrong node number.");
+
+  int ee = 0;
+  for (typename Graph::EdgeIt it(g); it != INVALID; ++it) {
+    ++ee;
+  }
+
+  check(ee == 2*e, "Wrong edge number.");
+  check(countEdges(g) == 2*e, "Wrong edge number.");
+
+  int uee = 0;
+  for (typename Graph::UndirEdgeIt it(g); it != INVALID; ++it) {
+    ++uee;
+  }
+
+  check(uee == e, "Wrong undir edge number.");
+  check(countUndirEdges(g) == e, "Wrong undir edge number.");
 }
 
 template <typename Graph>
@@ -108,8 +132,50 @@
   // print_items(g);
 
   check_item_counts(g,3,2);
+}
 
+void checkGridGraph(const GridGraph& g, int w, int h) {
+  check(g.width() == w, "Wrong width");
+  check(g.height() == h, "Wrong height");
+
+  for (int i = 0; i < w; ++i) {
+    for (int j = 0; j < h; ++j) {
+      check(g.col(g(i, j)) == i, "Wrong col");
+      check(g.row(g(i, j)) == j, "Wrong row");
+    }
+  }
+  
+  for (int i = 0; i < w; ++i) {
+    for (int j = 0; j < h - 1; ++j) {
+      check(g.source(g.down(g(i, j))) == g(i, j), "Wrong down");
+      check(g.target(g.down(g(i, j))) == g(i, j + 1), "Wrong down");
+    }
+    check(g.down(g(i, h - 1)) == INVALID, "Wrong down");
+  }
+
+  for (int i = 0; i < w; ++i) {
+    for (int j = 1; j < h; ++j) {
+      check(g.source(g.up(g(i, j))) == g(i, j), "Wrong up");
+      check(g.target(g.up(g(i, j))) == g(i, j - 1), "Wrong up");
+    }
+    check(g.up(g(i, 0)) == INVALID, "Wrong up");
+  }
+
+  for (int j = 0; j < h; ++j) {
+    for (int i = 0; i < w - 1; ++i) {
+      check(g.source(g.right(g(i, j))) == g(i, j), "Wrong right");
+      check(g.target(g.right(g(i, j))) == g(i + 1, j), "Wrong right");      
+    }
+    check(g.right(g(w - 1, j)) == INVALID, "Wrong right");    
+  }
 
+  for (int j = 0; j < h; ++j) {
+    for (int i = 1; i < w; ++i) {
+      check(g.source(g.left(g(i, j))) == g(i, j), "Wrong left");
+      check(g.target(g.left(g(i, j))) == g(i - 1, j), "Wrong left");      
+    }
+    check(g.left(g(0, j)) == INVALID, "Wrong left");    
+  }
 }
 
 int main() {
@@ -123,5 +189,13 @@
     check_item_counts(g, 5, 10);
   }
 
+  {
+    GridGraph g(5, 6);
+    check_item_counts(g, 30, 49);
+    checkGridGraph(g, 5, 6);
+  }
+
+  std::cout << __FILE__ ": All tests passed.\n";
+
   return 0;
 }



More information about the Lemon-commits mailing list