https://svn.lrde.epita.fr/svn/oln/branches/cleanup-2008/milena
Index: ChangeLog
from Thierry Geraud <thierry.geraud(a)lrde.epita.fr>
Make neighborhoods based on windows work.
* sandbox/geraud/cs2d/tuto_bis.cc: Rename as...
* doc/examples/tuto_bis.cc: ...this.
De-activate code.
Start with new material.
* mln/core/window.hh (is_symmetric): Fix the use of sym.
* mln/core/neighb.hh (neighb_fwd_niter, neighb_bkd_niter): New.
(fwd_niter, bkd_niter, niter): Update.
(change_window): New.
(from_to_): New overload.
* mln/core/concept/window.hh (operator==): Split decl and def.
* mln/core/concept/neighborhood.hh (to_window): Relax sig.
* mln/make/dual_neighb2d.hh: New.
* mln/convert/to_p_set.hh (D): Remove useless typedef.
* mln/win/multiple.hh (is_centered, is_symmetrical): New.
doc/examples/tuto_bis.cc | 96 ++++++++++++++-
mln/convert/to_p_set.hh | 3
mln/core/concept/neighborhood.hh | 5
mln/core/concept/window.hh | 13 +-
mln/core/neighb.hh | 237 ++++++++++++++++++++++++++++++++++++++-
mln/core/window.hh | 3
mln/make/dual_neighb2d.hh | 80 +++++++++++++
mln/win/multiple.hh | 28 ++++
8 files changed, 442 insertions(+), 23 deletions(-)
Index: doc/examples/tuto_bis.cc
--- doc/examples/tuto_bis.cc (revision 2268)
+++ doc/examples/tuto_bis.cc (working copy)
@@ -1,9 +1,20 @@
# include <vector>
+# include <mln/core/var.hh>
+
+# include <mln/core/alias/point2d.hh>
+# include <mln/core/alias/window2d.hh>
+# include <mln/make/win_multiple.hh>
+# include <mln/convert/to.hh>
+# include <mln/make/dual_neighb2d.hh>
+# include <mln/literal/origin.hh>
+# include <mln/core/site_set/p_set.hh>
+
+
+/*
# include <mln/core/image/image2d.hh>
# include <mln/core/image/sub_image.hh>
# include <mln/core/image/image_if.hh>
-# include <mln/core/image_if_value.hh>
# include <mln/core/alias/neighb2d.hh>
# include <mln/core/alias/window2d.hh>
@@ -21,13 +32,14 @@
# include <mln/level/transform.hh>
# include <mln/accu/mean.hh>
-# include "dbl_neighb.hh"
+*/
+/*
+
namespace mln
{
-
namespace level
{
@@ -117,19 +129,50 @@
}
is_point;
+*/
+
- struct is_row_odd_t
+namespace mln
{
- bool operator()(const mln::point2d& p) const
+
+ template <typename W, typename S>
+ void convert_to_site_set(const Window<W>& win,
+ const mln_psite(W)& p,
+ Site_Set<S>& s_)
{
- return p.row() % 2;
+ std::cout << "win -> pset" << std::endl;
+
+ S& s = exact(s_);
+ s.clear();
+
+ mln_qiter(W) q(exact(win), p);
+ for_all(q)
+ exact(s).insert(q);
}
- } is_row_odd;
-#define mln_VAR(Var, Expr) \
-typeof(Expr) Var = Expr;
+ template <typename N, typename S>
+ void convert_to_site_set(const Neighborhood<N>& nbh,
+ const mln_psite(N)& p,
+ Site_Set<S>& s_)
+ {
+ S& s = exact(s_);
+ s.clear();
+
+ mln_niter(N) n(exact(nbh), p);
+ for_all(n)
+ exact(s).insert(n);
+ }
+
+}
+
+
+
+ bool is_row_odd(const mln::point2d& p)
+ {
+ return p.row() % 2;
+ }
@@ -137,6 +180,39 @@
{
using namespace mln;
+ // e2c
+
+ bool e2c_h[] = { 0, 1, 0,
+ 0, 0, 0,
+ 0, 1, 0 };
+
+ bool e2c_v[] = { 0, 0, 0,
+ 1, 0, 1,
+ 0, 0, 0 };
+
+ mln_VAR( e2c, make::dual_neighb2d(is_row_odd, e2c_h, e2c_v) );
+
+// p_set<point2d> s;
+// convert_to_site_set(e2c, literal::origin, s);
+// std::cout << s << std::endl;
+
+ bool e2e_h[] = { 0, 0, 1, 0, 0,
+ 0, 1, 0, 1, 0,
+ 0, 0, 0, 0, 0,
+ 0, 1, 0, 1, 0,
+ 0, 0, 1, 0, 0 };
+
+ bool e2e_v[] = { 0, 0, 0, 0, 0,
+ 0, 1, 0, 1, 0,
+ 1, 0, 0, 0, 1,
+ 0, 1, 0, 1, 0,
+ 0, 0, 0, 0, 0 };
+
+ mln_VAR( e2e, make::dual_neighb2d(is_row_odd, e2e_h, e2e_v) );
+
+
+ /*
+
window2d c4 = convert::to_window(mln::c4());
@@ -274,4 +350,6 @@
// 5 5 5
// DONE!
+
+ */
}
Index: mln/core/window.hh
--- mln/core/window.hh (revision 2277)
+++ mln/core/window.hh (working copy)
@@ -186,7 +186,8 @@
window<D>::is_symmetric() const
{
window<D> cpy = *this;
- return cpy.sym() == *this;
+ cpy.sym();
+ return cpy == *this;
}
template <typename D>
Index: mln/core/neighb.hh
--- mln/core/neighb.hh (revision 2277)
+++ mln/core/neighb.hh (working copy)
@@ -39,24 +39,30 @@
namespace mln
{
+ // Forward declaration.
+ template <typename W> class neighb_fwd_niter;
+ template <typename W> class neighb_bkd_niter;
/*! \brief Adapter class from window to neighborhood.
*/
template <typename W>
- class neighb : public internal::neighborhood_base< mln_dpsite(W), neighb<D>
>,
+ class neighb : public internal::neighborhood_base< mln_dpsite(W), neighb<W>
>,
private mlc_is_a(W, Window)::check_t
{
public:
+ typedef W window;
+ const W& to_window() const { return win_; }
+
/// Forward site iterator associated type.
- typedef mln_fwd_qiter(W) fwd_niter;
+ typedef neighb_fwd_niter<W> fwd_niter;
/// Backward site iterator associated type.
- typedef mln_bkd_qiter(W) bkd_niter;
+ typedef neighb_bkd_niter<W> bkd_niter;
/// Site iterator associated type.
- typedef mln_qiter(W) niter;
+ typedef fwd_niter niter;
/// Constructor without argument.
@@ -68,6 +74,9 @@
/// Get the corresponding window.
const W& win() const;
+ /// Change the corresponding window.
+ void change_window(const W& new_win);
+
private:
W win_;
};
@@ -83,14 +92,94 @@
void
from_to_(const mln::neighb<W>& from, W& to);
+ template <typename W>
+ void
+ from_to_(const W& from, mln::neighb<W>& to);
+
} // end of namespace convert::impl
} // end of namespace convert
+ // neighb_fwd_niter<W>
+
+ template <typename W>
+ class neighb_fwd_niter
+ : public internal::site_relative_iterator_base< neighb<W>,
+ neighb_fwd_niter<W> >
+ {
+ public:
+
+ /// Constructor without argument.
+ neighb_fwd_niter();
+
+ template <typename P>
+ neighb_fwd_niter(const neighb<W>& nbh, const P& c);
+
+ /// Test the iterator validity.
+ bool is_valid_() const;
+
+ /// Invalidate the iterator.
+ void invalidate_();
+
+ /// Start an iteration.
+ void do_start_();
+
+ /// Go to the next point.
+ void do_next_();
+
+ /// Compute the current psite.
+ mln_psite(W) compute_p_() const;
+
+ protected:
+
+ mln_fwd_qiter(W) i_;
+ };
+
+
+
+ // neighb_bkd_niter<W>
+
+ template <typename W>
+ class neighb_bkd_niter
+ : public internal::site_relative_iterator_base< neighb<W>,
+ neighb_bkd_niter<W> >
+ {
+ public:
+
+ /// Constructor without argument.
+ neighb_bkd_niter();
+
+ template <typename P>
+ neighb_bkd_niter(const neighb<W>& nbh, const P& c);
+
+ /// Test the iterator validity.
+ bool is_valid_() const;
+
+ /// Invalidate the iterator.
+ void invalidate_();
+
+ /// Start an iteration.
+ void do_start_();
+
+ /// Go to the next point.
+ void do_next_();
+
+ /// Compute the current psite.
+ mln_psite(W) compute_p_() const;
+
+ protected:
+
+ mln_bkd_qiter(W) i_;
+ };
+
+
+
# ifndef MLN_INCLUDE_ONLY
+ // neighb<W>
+
template <typename W>
inline
neighb<W>::neighb()
@@ -101,8 +190,7 @@
inline
neighb<W>::neighb(const W& win)
{
- mln_precondition(win.is_neighbable_());
- win_ = win;
+ change_window(win);
}
template <typename W>
@@ -113,6 +201,17 @@
return win_;
}
+ template <typename W>
+ inline
+ void
+ neighb<W>::change_window(const W& new_win)
+ {
+ mln_precondition(new_win.is_neighbable_());
+ win_ = new_win;
+ }
+
+
+ // convert::impl::from_to_
namespace convert
{
@@ -126,11 +225,137 @@
to = from.win();
}
+ template <typename W>
+ void
+ from_to_(const W& from, mln::neighb<W>& to)
+ {
+ to.change_window(from);
+ }
+
} // end of namespace convert::impl
} // end of namespace convert
+ // neighb_fwd_niter<W>
+
+ template <typename W>
+ inline
+ neighb_fwd_niter<W>::neighb_fwd_niter()
+ {
+ }
+
+ template <typename W>
+ template <typename P>
+ inline
+ neighb_fwd_niter<W>::neighb_fwd_niter(const neighb<W>& nbh, const
P& c)
+ {
+ this->change_target(nbh);
+ this->center_at(c);
+ i_.center_at(c); // Always before change_target for this kind of iter.
+ i_.change_target(nbh.to_window());
+ }
+
+ template <typename W>
+ inline
+ bool
+ neighb_fwd_niter<W>::is_valid_() const
+ {
+ return i_.is_valid();
+ }
+
+ template <typename W>
+ inline
+ void
+ neighb_fwd_niter<W>::invalidate_()
+ {
+ i_.invalidate();
+ }
+
+ template <typename W>
+ inline
+ void
+ neighb_fwd_niter<W>::do_start_()
+ {
+ i_.start();
+ }
+
+ template <typename W>
+ inline
+ void
+ neighb_fwd_niter<W>::do_next_()
+ {
+ i_.next();
+ }
+
+ template <typename W>
+ inline
+ mln_psite(W)
+ neighb_fwd_niter<W>::compute_p_() const
+ {
+ return i_.compute_p_();
+ }
+
+
+ // neighb_bkd_niter<W>
+
+ template <typename W>
+ inline
+ neighb_bkd_niter<W>::neighb_bkd_niter()
+ {
+ }
+
+ template <typename W>
+ template <typename P>
+ inline
+ neighb_bkd_niter<W>::neighb_bkd_niter(const neighb<W>& nbh, const
P& c)
+ {
+ this->change_target(nbh);
+ this->center_at(c);
+ i_.center_at(c); // Always before change_target for this kind of iter.
+ i_.change_target(nbh.to_window());
+ }
+
+ template <typename W>
+ inline
+ bool
+ neighb_bkd_niter<W>::is_valid_() const
+ {
+ return i_.is_valid();
+ }
+
+ template <typename W>
+ inline
+ void
+ neighb_bkd_niter<W>::invalidate_()
+ {
+ i_.invalidate();
+ }
+
+ template <typename W>
+ inline
+ void
+ neighb_bkd_niter<W>::do_start_()
+ {
+ i_.start();
+ }
+
+ template <typename W>
+ inline
+ void
+ neighb_bkd_niter<W>::do_next_()
+ {
+ i_.next();
+ }
+
+ template <typename W>
+ inline
+ mln_psite(W)
+ neighb_bkd_niter<W>::compute_p_() const
+ {
+ return i_.compute_p_();
+ }
+
# endif // ! MLN_INCLUDE_ONLY
} // end of namespace mln
Index: mln/core/concept/window.hh
--- mln/core/concept/window.hh (revision 2277)
+++ mln/core/concept/window.hh (working copy)
@@ -79,10 +79,8 @@
template <typename Wl, typename Wr>
- bool operator==(const Window<Wl>& lhs, const Window<Wr>& rhs)
- {
- return exact(lhs).std_vector() == exact(rhs).std_vector();
- }
+ bool operator==(const Window<Wl>& lhs, const Window<Wr>& rhs);
+
# ifndef MLN_INCLUDE_ONLY
@@ -100,6 +98,13 @@
typedef mln_bkd_qiter(E) bkd_qiter;
}
+ template <typename Wl, typename Wr>
+ inline
+ bool operator==(const Window<Wl>& lhs, const Window<Wr>& rhs)
+ {
+ return exact(lhs).std_vector() == exact(rhs).std_vector();
+ }
+
# endif // ! MLN_INCLUDE_ONLY
} // end of namespace mln
Index: mln/core/concept/neighborhood.hh
--- mln/core/concept/neighborhood.hh (revision 2277)
+++ mln/core/concept/neighborhood.hh (working copy)
@@ -73,6 +73,7 @@
};
+
# ifndef MLN_INCLUDE_ONLY
template <typename E>
@@ -84,8 +85,10 @@
typedef mln_bkd_niter(E) bkd_niter;
typedef mln_window(E) window;
- window (E::*m)() const = & E::to_window;
+ bool m = (& E::to_window) == (& E::to_window);
m = 0;
+// const window& (E::*m)() const = & E::to_window;
+// m = 0;
}
# endif // ! MLN_INCLUDE_ONLY
Index: mln/make/dual_neighb2d.hh
--- mln/make/dual_neighb2d.hh (revision 0)
+++ mln/make/dual_neighb2d.hh (revision 0)
@@ -0,0 +1,80 @@
+// Copyright (C) 2008 EPITA Research and Development Laboratory
+//
+// 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_MAKE_DUAL_NEIGHB2D_HH
+# define MLN_MAKE_DUAL_NEIGHB2D_HH
+
+/*! \file mln/make/dual_neighb2d.hh
+ *
+ * \brief Routine to create a dual neighborhood.
+ */
+
+# include <mln/core/alias/window2d.hh>
+# include <mln/win/multiple.hh>
+# include <mln/core/neighb.hh>
+
+
+namespace mln
+{
+
+ namespace make
+ {
+
+ template <typename A, unsigned St, unsigned Sf>
+ neighb< win::multiple<window2d, bool(*)(A)> >
+ dual_neighb2d(bool (*test)(A),
+ bool const (&when_true) [St],
+ bool const (&when_false)[Sf]);
+
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+
+ template <typename A, unsigned St, unsigned Sf>
+ inline
+ neighb< win::multiple<window2d, bool(*)(A)> >
+ dual_neighb2d(bool (*test)(A),
+ bool const (&when_true) [St],
+ bool const (&when_false)[Sf])
+ {
+ typedef win::multiple<window2d, bool(*)(A)> W;
+ W wm(test);
+ wm.set_window(false, convert::to<window2d>(when_false)); // 0
+ wm.set_window(true, convert::to<window2d>(when_true) ); // 1
+ neighb<W> tmp(wm);
+ return tmp;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace mln::make
+
+} // end of namespace mln
+
+
+#endif // ! MLN_MAKE_DUAL_NEIGHB2D_HH
Index: mln/convert/to_p_set.hh
--- mln/convert/to_p_set.hh (revision 2277)
+++ mln/convert/to_p_set.hh (working copy)
@@ -1,4 +1,4 @@
-// Copyright (C) 2007 EPITA Research and Development Laboratory
+// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -112,7 +112,6 @@
inline
p_set<mln_site(W)> to_p_set(const Window<W>& win)
{
- typedef mln_dpsite(W) D;
typedef mln_site(W) P;
p_set<P> pset;
mln_qiter(W) q(exact(win), P::origin);
Index: mln/win/multiple.hh
--- mln/win/multiple.hh (revision 2277)
+++ mln/win/multiple.hh (working copy)
@@ -78,6 +78,10 @@
const mln_dpsite(W)& ith_dp_around(unsigned i, const mln_psite(W)& p)
const;
+ bool is_centered() const;
+
+ bool is_symmetric() const;
+
private:
util::array<W> win_;
@@ -179,6 +183,30 @@
template <typename W, typename F>
inline
+ bool
+ multiple<W,F>::is_centered() const
+ {
+ mln_precondition(win_.nelements() >= 1);
+ for (unsigned i = 0; i < win_.nelements(); ++i)
+ if (! win_[i].is_centered())
+ return false;
+ return true;
+ }
+
+ template <typename W, typename F>
+ inline
+ bool
+ multiple<W,F>::is_symmetric() const
+ {
+ mln_precondition(win_.nelements() >= 1);
+ for (unsigned i = 0; i < win_.nelements(); ++i)
+ if (! win_[i].is_symmetric())
+ return false;
+ return true;
+ }
+
+ template <typename W, typename F>
+ inline
unsigned
multiple<W,F>::size_around(const mln_psite(W)& p) const
{