* mln/accu/center.hh: New accu.
* mln/accu/all.hh,
* mln/accu/essential.hh: add center.hh.
* mln/make/all.hh,
* mln/make/essential.hh,
* mln/debug/essential.hh,
* mln/debug/all.hh: update includes.
* mln/debug/graph.hh: Rename as...
* mln/debug/draw_graph.hh: ...this.
* mln/make/graph.hh: Add make::graph().
* mln/util/array.hh: cleanup.
* mln/util/edge.hh: cleanup comments.
* mln/util/graph.hh: add new constructors.
---
milena/ChangeLog | 25 ++++
milena/mln/accu/all.hh | 1 +
milena/mln/accu/center.hh | 154 +++++++++++++++++++++++++
milena/mln/accu/essential.hh | 1 +
milena/mln/debug/all.hh | 10 +-
milena/mln/debug/{graph.hh => draw_graph.hh} | 80 +++++---------
milena/mln/debug/essential.hh | 9 +-
milena/mln/make/all.hh | 1 +
milena/mln/make/essential.hh | 7 +-
milena/mln/make/graph.hh | 159 ++++++++++++++++++++++++++
milena/mln/util/array.hh | 35 +++----
milena/mln/util/edge.hh | 2 +-
milena/mln/util/graph.hh | 37 ++++++
13 files changed, 434 insertions(+), 87 deletions(-)
create mode 100644 milena/mln/accu/center.hh
rename milena/mln/debug/{graph.hh => draw_graph.hh} (53%)
create mode 100644 milena/mln/make/graph.hh
diff --git a/milena/ChangeLog b/milena/ChangeLog
index f6f62e5..813df7d 100644
--- a/milena/ChangeLog
+++ b/milena/ChangeLog
@@ -1,3 +1,28 @@
+2008-11-18 Guillaume Lazzara <z(a)lrde.epita.fr>
+
+ Update graph related classes.
+
+ * mln/accu/center.hh: New accu.
+
+ * mln/accu/all.hh,
+ * mln/accu/essential.hh: add center.hh.
+
+ * mln/make/all.hh,
+ * mln/make/essential.hh,
+ * mln/debug/essential.hh,
+ * mln/debug/all.hh: update includes.
+
+ * mln/debug/graph.hh: Rename as...
+ * mln/debug/draw_graph.hh: ...this.
+
+ * mln/make/graph.hh: Add make::graph().
+
+ * mln/util/array.hh: cleanup.
+
+ * mln/util/edge.hh: cleanup comments.
+
+ * mln/util/graph.hh: add new constructors.
+
2008-11-19 Thierry Geraud <thierry.geraud(a)lrde.epita.fr>
Update canvas labelingand labeling level.
diff --git a/milena/mln/accu/all.hh b/milena/mln/accu/all.hh
index cda8581..1d8b9bc 100644
--- a/milena/mln/accu/all.hh
+++ b/milena/mln/accu/all.hh
@@ -58,6 +58,7 @@ namespace mln
# include <mln/accu/bbox.hh>
# include <mln/accu/count.hh>
+# include <mln/accu/center.hh>
//# include <mln/accu/count_adjacent_vertices.hh>
# include <mln/accu/height.hh>
# include <mln/accu/histo.hh>
diff --git a/milena/mln/accu/center.hh b/milena/mln/accu/center.hh
new file mode 100644
index 0000000..2aacfce
--- /dev/null
+++ b/milena/mln/accu/center.hh
@@ -0,0 +1,154 @@
+// Copyright (C) 2008 EPITA Research and Development Laboratory (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to
+// produce an executable, this file does not by itself cause the
+// resulting executable to be covered by the GNU General Public
+// License. This exception does not however invalidate any other
+// reasons why the executable file might be covered by the GNU General
+// Public License.
+
+#ifndef MLN_ACCU_CENTER_HH
+# define MLN_ACCU_CENTER_HH
+
+/// \file mln/accu/center.hh
+///
+/// Define an accumulator that computes the center of a site set.
+
+# include <mln/accu/internal/base.hh>
+# include <mln/accu/bbox.hh>
+
+namespace mln
+{
+
+ namespace accu
+ {
+
+
+ /// Generic center accumulator class.
+ template <typename P>
+ struct center : public mln::accu::internal::base< P , center<P> >
+ {
+ typedef P argument;
+ typedef P result;
+
+ center();
+
+ /// Manipulators.
+ /// \{
+ void init();
+ void take(const argument& t);
+ void take(const center<P>& other);
+ /// \}
+
+ /// Get the value of the accumulator.
+ P to_result() const;
+ operator P () const;
+
+ /// Check whether this accu is able to return a result.
+ bool is_valid() const;
+
+ protected:
+ accu::bbox<P> bbox_;
+ };
+
+ namespace meta
+ {
+
+ /// Meta accumulator for center.
+ struct center : public Meta_Accumulator< center >
+ {
+
+ template <typename P>
+ struct with
+ {
+ typedef accu::center<P> ret;
+ };
+
+ };
+
+ } // end of namespace mln::accu::meta
+
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename P>
+ inline
+ center<P>::center()
+ {
+ init();
+ }
+
+ template <typename P>
+ inline
+ void
+ center<P>::init()
+ {
+ bbox_.init();
+ }
+
+ template <typename P>
+ inline
+ void center<P>::take(const argument& t)
+ {
+ bbox_.take(t);
+ }
+
+ template <typename P>
+ inline
+ void
+ center<P>::take(const center<P>& other)
+ {
+ bbox_.take(other.bbox_);
+ }
+
+ template <typename P>
+ inline
+ P
+ center<P>::to_result() const
+ {
+ return bbox_.to_result().center();
+ }
+
+ template <typename P>
+ inline
+ center<P>::operator P() const
+ {
+ return P(bbox_.to_result().center());
+ }
+
+ template <typename P>
+ inline
+ bool
+ center<P>::is_valid() const
+ {
+ return bbox_.is_valid();
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace mln::accu
+
+} // end of namespace mln
+
+
+#endif // ! MLN_ACCU_CENTER_HH
diff --git a/milena/mln/accu/essential.hh b/milena/mln/accu/essential.hh
index 18498f2..e8c57cc 100644
--- a/milena/mln/accu/essential.hh
+++ b/milena/mln/accu/essential.hh
@@ -33,6 +33,7 @@
/// File that includes the most useful accumulator types.
# include <mln/accu/bbox.hh>
+# include <mln/accu/center.hh>
# include <mln/accu/count.hh>
# include <mln/accu/histo.hh>
# include <mln/accu/max.hh>
diff --git a/milena/mln/debug/all.hh b/milena/mln/debug/all.hh
index a17fb37..a0a27c6 100644
--- a/milena/mln/debug/all.hh
+++ b/milena/mln/debug/all.hh
@@ -1,4 +1,5 @@
// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
+// (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -28,10 +29,9 @@
#ifndef MLN_DEBUG_ALL_HH
# define MLN_DEBUG_ALL_HH
-/*! \file mln/debug/all.hh
- *
- * \brief File that includes all debug-related routines.
- */
+/// \file mln/debug/all.hh
+///
+/// File that includes all debug-related routines.
namespace mln
@@ -48,7 +48,7 @@ namespace mln
# include <mln/debug/colorize.hh>
# include <mln/debug/format.hh>
-//# include <mln/debug/graph.hh>
+# include <mln/debug/draw_graph.hh>
# include <mln/debug/iota.hh>
# include <mln/debug/println.hh>
# include <mln/debug/println_with_border.hh>
diff --git a/milena/mln/debug/graph.hh b/milena/mln/debug/draw_graph.hh
similarity index 53%
rename from milena/mln/debug/graph.hh
rename to milena/mln/debug/draw_graph.hh
index e92b802..159b974 100644
--- a/milena/mln/debug/graph.hh
+++ b/milena/mln/debug/draw_graph.hh
@@ -30,7 +30,10 @@
# define MLN_DEBUG_DRAW_GRAPH_HH
/// \file mln/debug/graph.hh
+///
/// \brief Draw an (classical) image from a mln::graph_image.
+///
+/// \todo write a version for graph images.
# include <mln/pw/image.hh>
# include <mln/level/fill.hh>
@@ -43,83 +46,56 @@ namespace mln
namespace debug
{
- /*! \brief Draw an image \p ima from a mln::p_graph \p pg, with
- * value \p vertex_v for vertices, value \p edge_v for edges and 0 for
- * the background.
- *
- * \param[in,out] ima The image to be drawn.
- * \param[in] pv The p_vertices which contains vertices positions.
- * \param[in] vertex_v The value to assign to pixels which contains
- * vertices.
- * \param[in] edge_v The value to assign to pixels which contains
- * edges.
- */
+ /// Draw an image \p ima from a mln::p_graph \p pg, with
+ /// value \p vertex_v for vertices, value \p edge_v for edges and 0 for
+ /// the background.
+ ///
+ /// \param[in,out] ima The image to be drawn.
+ /// \param[in] pv The p_vertices which contains vertices positions.
+ /// \param[in] vertex_v The value to assign to pixels which contains
+ /// vertices.
+ /// \param[in] edge_v The value to assign to pixels which contains
+ /// edges.
template <typename I, typename G, typename F>
void
draw_graph(Image<I>& ima, const p_vertices<G, F>& pv,
mln_value(I) vertex_v, mln_value(I) edge_v);
- /*! \brief Draw an image \p ima from a mln::graph_image \p gi.
- *
- * The background is filled with value 0.
- *
- * \param[in,out] ima The image to be drawn.
- * \param[in] gi The graph_image which contains the vertices,
- * edges positions and the values of it.
- * \param[in] edge_v The value to assign to pixels which contains
- * edges, defaulting to 1.
- */
- // FIXME: The type of the last argument cannot always been
- // constructed from `int'! We should remove this last argument.
-// template <typename I, typename P, typename V>
-// void
-// draw_graph(Image<I>& ima, const graph_image<P, V>& gi,
-// mln_value(I) edge_v = 1);
+
# ifndef MLN_INCLUDE_ONLY
+
+
// FIXME: Add assertions on the size of the image: it must be large
// enough to hold the representation of the graph/graph_image.
template <typename I, typename G, typename F>
inline
void
- draw_graph(Image<I>& ima, const p_vertices<G, F>& pv,
- mln_value(I) vertex_v, mln_value(I) edge_v)
+ draw_graph(Image<I>& ima,
+ const p_vertices<G, F>& pv,
+ mln_value(I) vertex_v,
+ mln_value(I) edge_v)
{
- // Debug the background.
- level::fill(ima, 0);
+ // Fill the background.
+ level::fill(ima, literal::black);
- // Debug the lines (edges).
+ // Draw edges.
const G& g = pv.graph();
typedef p_vertices<G, F> pv_t;
mln_edge_iter(G) ei(g);
for_all(ei)
draw::line(exact(ima), pv(ei.v1()), pv(ei.v2()), edge_v);
- // Debug the points (vertices).
+ // Draw vertices.
mln_piter(pv_t) p(pv);
for_all(p)
- exact(ima)(p) = vertex_v;
+ if (exact(ima).has(p))
+ exact(ima)(p) = vertex_v;
}
-/*
- template <typename I, typename P, typename V>
- inline
- void
- draw_graph(Image<I>& ima, const graph_image<P, V>& gi,
- mln_value(I) edge_v)
- {
- // Debug the background.
- level::fill(ima, 0);
- // Debug the lines (edges).
- for (unsigned l = 0; l < gi.domain().nedges(); ++l)
- line (exact(ima), gi.vertex1(l), gi.vertex2(l), edge_v);
- // Debug the points (vertices).
- for (unsigned p = 0; p < gi.domain().nvertices(); ++p)
- exact(ima)(gi.domain().point_from_id(p)) = gi.vertex_values()[p];
- }
-*/
+
# endif // ! MLN_INCLUDE_ONLY
@@ -127,4 +103,4 @@ namespace mln
} // end of namespace mln
-#endif // MLN_DEBUG_DRAW_GRAPH_HH
+#endif // ! MLN_DEBUG_DRAW_GRAPH_HH
diff --git a/milena/mln/debug/essential.hh b/milena/mln/debug/essential.hh
index 122a6c0..a28563b 100644
--- a/milena/mln/debug/essential.hh
+++ b/milena/mln/debug/essential.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2008 EPITA Research and Development Laboratory (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -28,10 +28,9 @@
#ifndef MLN_DEBUG_ESSENTIAL_HH
# define MLN_DEBUG_ESSENTIAL_HH
-/*! \file mln/debug/essential.hh
- *
- * \brief File that includes essential debug-related routines.
- */
+/// \file mln/debug/essential.hh
+///
+/// File that includes essential debug-related routines.
# include <mln/debug/all.hh>
diff --git a/milena/mln/make/all.hh b/milena/mln/make/all.hh
index 910d943..5dc232c 100644
--- a/milena/mln/make/all.hh
+++ b/milena/mln/make/all.hh
@@ -48,6 +48,7 @@ namespace mln
# include <mln/make/box3d.hh>
# include <mln/make/dpoint2d_h.hh>
# include <mln/make/dual_neighb.hh>
+# include <mln/make/graph.hh>
# include <mln/make/image.hh>
# include <mln/make/image2d.hh>
# include <mln/make/mat.hh>
diff --git a/milena/mln/make/essential.hh b/milena/mln/make/essential.hh
index 856e75a..33aa0e7 100644
--- a/milena/mln/make/essential.hh
+++ b/milena/mln/make/essential.hh
@@ -29,10 +29,9 @@
#ifndef MLN_MAKE_ESSENTIAL_HH
# define MLN_MAKE_ESSENTIAL_HH
-/*! \file mln/make/essential.hh
- *
- * \brief File that includes essential make routines.
- */
+/// \file mln/make/essential.hh
+///
+/// File that includes essential make routines.
# include <mln/make/dual_neighb.hh>
# include <mln/make/image.hh>
diff --git a/milena/mln/make/graph.hh b/milena/mln/make/graph.hh
new file mode 100644
index 0000000..c3ae618
--- /dev/null
+++ b/milena/mln/make/graph.hh
@@ -0,0 +1,159 @@
+// Copyright (C) 2008 EPITA Research and Development Laboratory (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// of the GNU General Public License version 2 as published by the
+// Free Software Foundation.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this library; see the file COPYING. If not, write to
+// the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+// Boston, MA 02111-1307, USA.
+//
+// As a special exception, you may use this file as part of a free
+// software library without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to
+// produce an executable, this file does not by itself cause the
+// resulting executable to be covered by the GNU General Public
+// License.
+// reasons why the executable file might be covered by the GNU General
+// Public License.
+
+#ifndef MLN_MAKE_GRAPH_HH
+# define MLN_MAKE_GRAPH_HH
+
+/// \file mln/make/graph.hh
+///
+/// Create a graph from an influence zone image.
+///
+/// \sa transform::influence_zone_geodesic.
+
+# include <mln/util/graph.hh>
+
+namespace mln
+{
+
+ namespace make
+ {
+
+ /// Create a graph from an influence zone image.
+ ///
+ /// \param[in] iz influence zone image.
+ /// \param[in] nlabels number of influence zone in \p iz.
+ ///
+ /// \return util::graph Graph based on the adjacency of the influence zones.
+ template <typename I>
+ util::graph graph(const Image<I>& iz, mln_value(I) nlabels);
+
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ namespace internal
+ {
+
+ template <typename I>
+ void
+ graph_tests(const Image<I>& iz, mln_value(I))
+ {
+ mln_precondition(exact(iz).has_data());
+
+ (void) iz;
+ }
+
+ } // end of namespace mln::make::internal
+
+
+
+ namespace impl
+ {
+
+ namespace generic
+ {
+
+ template <typename I>
+ util::graph
+ graph(const Image<I>& iz_, mln_value(I) nlabels)
+ {
+ trace::entering("make::impl::generic::graph");
+
+ internal::graph_tests(iz_, nlabels);
+ const I& iz = exact(iz_);
+
+ util::graph g;
+ g.add_vertices(nlabels + 1);
+
+ mln_piter(I) p(iz.domain());
+ for_all(p)
+ {
+ // Checking 'forward' neighboors and create an edge if necessary.
+ for (unsigned dim = 0; dim < mln_site_(I)::dim; ++dim)
+ {
+ mln_site(I) n = p;
+ ++n[dim];
+
+ // FIXME: check that calling iz.domain().has() is correct
+ // and that we don't prefer iz.has().
+ if (iz.domain().has(n) && iz(p) != iz(n))
+ g.add_edge(iz(p), iz(n));
+ }
+ }
+
+ trace::exiting("make::impl::generic::graph");
+ return g;
+ }
+
+ } // end of namespace mln::make::impl::generic
+
+ } // end of namespace mln::make::impl
+
+
+
+ namespace internal
+ {
+
+ template <typename I>
+ util::graph
+ graph_dispatch(const Image<I>& iz, mln_value(I) nlabels)
+ {
+ return make::impl::generic::graph(iz, nlabels);
+ }
+
+ } // end of namespace mln::make::internal
+
+
+
+ // Facade
+
+ template <typename I>
+ inline
+ util::graph
+ graph(const Image<I>& iz, mln_value(I) nlabels)
+ {
+ trace::entering("make::graph");
+
+ internal::graph_tests(iz, nlabels);
+
+ util::graph g = internal::graph_dispatch(iz, nlabels);
+
+ trace::exiting("make::graph");
+ return g;
+ }
+
+
+# endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace mln::make
+
+} // end of namespace mln
+
+
+#endif // ! MLN_MAKE_GRAPH_HH
diff --git a/milena/mln/util/array.hh b/milena/mln/util/array.hh
index 66b41a8..5f49839 100644
--- a/milena/mln/util/array.hh
+++ b/milena/mln/util/array.hh
@@ -1,4 +1,4 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2008 EPITA Research and Development Laboratory (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -28,13 +28,12 @@
#ifndef MLN_UTIL_ARRAY_HH
# define MLN_UTIL_ARRAY_HH
-/*! \file mln/util/array.hh
- *
- * \brief Definition of mln::util::array.
- *
- * \todo Zed: Add a lazy removal method (based on an extra attribute
- * std::vector<bool> has_). Then add a purge/compress method.
- */
+/// \file mln/util/array.hh
+///
+/// Definition of mln::util::array.
+///
+/// \todo Zed: Add a lazy removal method (based on an extra attribute
+/// std::vector<bool> has_). Then add a purge/compress method.
# include <vector>
# include <iostream>
@@ -55,15 +54,12 @@ namespace mln
template <typename T> class array_bkd_iter;
- /*! \brief A dynamic array class.
- *
- *
- *
- * Elements are stored by copy. Implementation is lazy.
- *
- * The parameter \c T is the element type, which shall not be
- * const-qualified.
- */
+ /// A dynamic array class.
+ ///
+ /// Elements are stored by copy. Implementation is lazy.
+ ///
+ /// The parameter \c T is the element type, which shall not be
+ /// const-qualified.
template <typename T>
class array : public Object< mln::util::array<T> >
{
@@ -141,7 +137,7 @@ namespace mln
/// Operator<<.
template <typename T>
std::ostream& operator<<(std::ostream& ostr,
- const mln::util::array<T>& a);
+ const mln::util::array<T>& a);
@@ -240,7 +236,6 @@ namespace mln
# ifndef MLN_INCLUDE_ONLY
-
// util::array<T>
@@ -546,7 +541,7 @@ namespace mln
template <typename T>
std::ostream& operator<<(std::ostream& ostr,
- const mln::util::array<T>& a)
+ const mln::util::array<T>& a)
{
ostr << '[';
const unsigned n = a.nelements();
diff --git a/milena/mln/util/edge.hh b/milena/mln/util/edge.hh
index a6ce803..ba34a12 100644
--- a/milena/mln/util/edge.hh
+++ b/milena/mln/util/edge.hh
@@ -299,7 +299,7 @@ namespace mln
std::ostream&
operator<<(std::ostream& ostr, const edge<G>& p)
{
- return ostr << p.id();
+ return ostr << "(" << p.v1() << "," <<
p.v2() << ")";
}
template <typename G>
diff --git a/milena/mln/util/graph.hh b/milena/mln/util/graph.hh
index 1b22c43..7c003a2 100644
--- a/milena/mln/util/graph.hh
+++ b/milena/mln/util/graph.hh
@@ -62,6 +62,9 @@ namespace mln
typedef std::set<util::ord_pair<unsigned> > edges_set_t;
data();
+ /// Constructor.
+ /// Allocate enough space in order to support \p nvertices vertices.
+ data(unsigned nvertices);
~data();
/// The vertices.
@@ -134,19 +137,29 @@ namespace mln
/// \}
/// \}
+ /// Constructor.
graph();
+ /// Construct a graph with \p nvertices vertices.
+ graph(unsigned nvertices);
/// Vertex oriented.
/// \{
+
/// Shortcuts factoring the insertion of vertices and edges.
/// \{
+
/// Add a vertex.
///
/// \return The id of the new vertex.
unsigned add_vertex();
+ /// Add \p n vertices to the graph.
+ ///
+ /// \return A range of vertex ids.
+ std::pair<unsigned, unsigned> add_vertices(unsigned n);
+
/// Return the vertex whose id is \a v.
/// \{
vertex_t vertex(unsigned id_v) const;
@@ -239,6 +252,12 @@ namespace mln
}
inline
+ data<util::graph>::data(unsigned nvertices)
+ {
+ vertices_.resize(nvertices);
+ }
+
+ inline
data<util::graph>::~data()
{
}
@@ -254,6 +273,12 @@ namespace mln
this->data_ = new mln::internal::data<util::graph>();
}
+ inline
+ graph::graph(unsigned nvertices)
+ {
+ this->data_ = new mln::internal::data<util::graph>(nvertices);
+ }
+
/*---------------.
| Vertex related |
`---------------*/
@@ -270,6 +295,18 @@ namespace mln
}
inline
+ std::pair<unsigned, unsigned>
+ graph::add_vertices(unsigned n)
+ {
+ /* FIXME: This is not thread-proof (these two lines should
+ form an atomic section). */
+ data_->vertices_.resize(data_->vertices_.size() + n);
+
+ return std::make_pair(v_nmax() - n,
+ v_nmax() - 1);
+ }
+
+ inline
graph::vertex_t
graph::vertex(unsigned id_v) const
{
--
1.5.6.5