https://svn.lrde.epita.fr/svn/oln/branches/cleanup-2008/milena
Index: ChangeLog
from Thierry Geraud <thierry.geraud(a)lrde.epita.fr>
Make the tricky morpho example fully work.
* mln/core/site_set/p_centered.hh: New.
* mln/core/site_set/all.hh: Update.
* mln/core/image/extended.hh: New.
* mln/core/image/extension_fun.hh,
* mln/core/image/extension_ima.hh,
* mln/core/image/extension_val.hh (ch_value): New.
The extension is propagated to a concrete type iff it can
work.
(todo): New.
* mln/core/image/image1d.hh,
* mln/core/image/image3d.hh (line_piter): De-activate cause it
does not work yet.
* mln/core/point.hh (point): Add explicit to the 1D ctor.
* mln/level/sort_psites.hh: Update.
* mln/border/fill.hh,
* mln/border/mirror.hh: Update.
* mln/fun/i2v/array.hh: New.
* mln/win/all.hh: Update.
* mln/win/multiple.hh (i_): Fix warning.
* doc/examples/tuto_bis.cc: Update.
doc/examples/tuto_bis.cc | 224 +++++++++++++++++------------
mln/border/fill.hh | 4
mln/border/mirror.hh | 30 ++--
mln/core/image/extended.hh | 226 ++++++++++++++++++++++++++++++
mln/core/image/extension_fun.hh | 11 +
mln/core/image/extension_ima.hh | 11 +
mln/core/image/extension_val.hh | 11 +
mln/core/image/image1d.hh | 1
mln/core/image/image3d.hh | 4
mln/core/point.hh | 2
mln/core/site_set/all.hh | 14 +
mln/core/site_set/p_centered.hh | 300 ++++++++++++++++++++++++++++++++++++++++
mln/fun/i2v/array.hh | 147 +++++++++++++++++++
mln/level/sort_psites.hh | 13 +
mln/win/all.hh | 4
mln/win/multiple.hh | 2
16 files changed, 877 insertions(+), 127 deletions(-)
Index: doc/examples/tuto_bis.cc
--- doc/examples/tuto_bis.cc (revision 2280)
+++ doc/examples/tuto_bis.cc (working copy)
@@ -2,37 +2,28 @@
# include <mln/core/image/image2d.hh>
# include <mln/core/image/image_if.hh>
+# include <mln/core/image/extended.hh>
# include <mln/core/routine/extend.hh>
# include <mln/core/alias/window2d.hh>
+# include <mln/core/alias/neighb2d.hh>
# include <mln/make/dual_neighb2d.hh>
+# include <mln/core/site_set/p_centered.hh>
+# include <mln/literal/origin.hh>
-# include <mln/debug/println.hh>
+# include <mln/accu/min_max.hh>
+# include <mln/accu/mean.hh>
+
+# include <mln/fun/i2v/array.hh>
# include <mln/fun/p2v/iota.hh>
# include <mln/level/paste.hh>
# include <mln/level/fill.hh>
+# include <mln/level/transform.hh>
-# include <mln/accu/min_max.hh>
-# include <mln/morpho/meyer_wst.hh>
-
-
-/*
-# include <vector>
-
-# include <mln/core/image/sub_image.hh>
-
-# include <mln/core/alias/neighb2d.hh>
-# include <mln/core/alias/window2d.hh>
-# include <mln/convert/to_window.hh>
-
-# include <mln/morpho/dilation.hh>
# include <mln/morpho/meyer_wst.hh>
-# include <mln/level/transform.hh>
-# include <mln/accu/mean.hh>
-
-*/
+# include <mln/debug/println.hh>
/*
@@ -63,18 +54,49 @@
} // mln::level
+
+} // mln
+
+*/
+
+
+namespace mln
+{
+
+ namespace border
+ {
+
+ template <typename I>
+ void
+ fill(I& ima, const mln_value(I)& v)
+ {
+ const int nrows = ima.nrows();
+ const int ncols = ima.ncols();
+ for (int r = -1; r <= nrows; ++r)
+ {
+ ima.at(r, -1) = v;
+ ima.at(r, ncols) = v;
+ }
+ for (int c = -1; c <= ncols; ++c)
+ {
+ ima.at(-1, c) = v;
+ ima.at(nrows, c) = v;
+ }
+ }
+
+ } // mln::border
+
namespace accu
{
- template <typename A_, typename I, typename L, typename R>
+ template <typename A_, typename I, typename L, typename V>
inline
void
compute(const Image<I>& input_,
const Image<L>& label_,
- std::vector<R>& v)
+ V& v)
{
mlc_is_a(A_, Meta_Accumulator)::check();
-
trace::entering("accu::compute");
const I& input = exact(input_);
@@ -89,51 +111,13 @@
a[label(p)].take(input(p));
for (unsigned l = 1; l < n; ++l)
- v[l] = a[l].to_result();
+ v(l) = a[l];
trace::exiting("accu::compute");
}
} // mln::accu
-} // mln
-
-
-*/
-
-
-namespace mln
-{
-
- template <typename W, typename S>
- void convert_to_site_set(const Window<W>& win,
- const mln_psite(W)& p,
- Site_Set<S>& s_)
- {
- 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);
- }
-
- 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);
- }
-
-
namespace morpho
{
@@ -157,42 +141,75 @@
return output;
}
+ template <typename I, typename N>
+ mln_concrete(I)
+ dilation(const I& input, const N& nbh)
+ {
+ typedef mln_value(I) V;
+ // extension::fill(input, mln_min(V));
- } // mln::morpho
+ mln_concrete(I) output;
+ initialize(output, input);
+ accu::max_<V> m;
+ mln_piter(I) p(input.domain());
+ mln_niter(N) n(nbh, p);
+ for_all(p)
+ {
+ m.init();
+ for_all(n) if (input.has(n))
+ m.take(input(n));
+ output(p) = m;
+ }
+ return output;
+ }
+
+ } // mln::morpho
} // mln
+
// Functions
+inline
bool is_row_odd(const mln::point2d& p)
{
return p.row() % 2;
}
+inline
bool is_cell(const mln::point2d& p)
{
return p.row() % 2 == 0 && p.col() % 2 == 0;
}
+inline
bool is_edge(const mln::point2d& p)
{
return p.row() % 2 + p.col() % 2 == 1;
}
+inline
bool is_point(const mln::point2d& p)
{
return p.row() % 2 && p.col() % 2;
}
+inline
+bool is_not_edge(const mln::point2d& p)
+{
+ return ! is_edge(p);
+}
+
int main()
{
using namespace mln;
+
// e2c
bool e2c_h[] = { 0, 1, 0,
@@ -221,6 +238,16 @@
+// {
+// p_centered<e2e_t::window> wc(e2e.to_window(), literal::origin);
+// std::cout << wc << std::endl;
+
+// p_set<point2d> s;
+// s += wc;
+// std::cout << s << std::endl;
+// }
+
+
image2d<int> ima(3, 5);
@@ -244,29 +271,26 @@
// 1 1
- unsigned nbasins;
- mln_VAR(wst, morpho::meyer_wst(edge, e2e, nbasins));
- // ^^^
- // edge -> neighboring edges
- debug::println(wst);
- // 2 2
- // 0 0 0
- // 1 1
-
- std::cout << nbasins << " bassins" << std::endl;
- // 2 bassins
-
-
+ image2d<unsigned> label(ima.bbox(), 1);
+ border::fill(label, 0);
+ level::fill(label, 9);
+ debug::println(label);
+ // 9 9 9 9 9
+ // 9 9 9 9 9
+ // 9 9 9 9 9
- /*
- window2d c4 = convert::to_window(mln::c4());
+ mln_VAR(wst, label | is_edge);
+ debug::println(wst);
+ // 9 9
+ // 9 9 9
+ // 9 9
unsigned nbasins;
- mln_VAR(wst, morpho::meyer_wst(edge, nbh_e2e, nbasins));
- // ^^^^^^^
- // edge -> neighbooring edges
+ level::fill(wst, morpho::meyer_wst(edge, e2e, nbasins));
+ // ^^^
+ // edge -> neighboring edges
debug::println(wst);
// 2 2
// 0 0 0
@@ -276,11 +300,15 @@
// 2 bassins
+
+
// '0' IS THE TAG VALUE FOR THE WATERSHED LINE
// THE OTHER VALUES ARE THE REGION LABELS
- std::cout << "the watershed line = " << (wst | 0).domain()
<< std::endl;
+ mln_VAR(wst_line, wst | (pw::value(wst) == pw::cst(0u))); // FIXME: wst | 0
+ std::cout << "the watershed line = " << wst_line.domain()
<< std::endl
+ << std::endl;
// the watershed line = {(1,0)(1,2)(1,4)}
// ^^^^^
// meaning (row = 1, col = 0)
@@ -298,22 +326,31 @@
// row
- // YET THOSE VALUES ARE ON EDGES, NOT ON CELLS...
+ // YET THOSE VALUES ARE ON EDGES, NOT ON CELLS...
- mln_VAR(label, wst.full());
debug::println(label);
- // 0 2 0 2 0
- // 0 0 0 0 0
- // 0 1 0 1 0
+ // 9 2 9 2 9
+ // 0 9 0 9 0
+ // 9 1 9 1 9
- level::paste(morpho::dilation(label | is_cell, c4), label);
+
+ mln_VAR(lab, label | is_cell);
+ debug::println(lab);
+ // 9 9 9
+ //
+ // 9 9 9
+
+ level::paste(morpho::dilation(extend(lab, pw::value(label)),
+ c4()),
+ label);
debug::println(label);
// 2 2 2 2 2
- // 0 0 0 0 0
+ // 0 9 0 9 0
// 1 1 1 1 1
- debug::println(label | is_cell);
+
+ debug::println(lab);
// 2 2 2
//
// 1 1 1
@@ -332,18 +369,17 @@
// NOW WE WANT TO MODIFY THE INPUT IMAGE TO FLATTEN REGIONS...
- std::vector<int> m(nbasins + 1);
+ fun::i2v::array<int> m(nbasins + 1);
accu::compute<accu::mean>(cell, label, m);
for (unsigned i = 1; i <= nbasins; ++i)
- std::cout << "mean value of basin " << i << " is
" << m[i] << std::endl;
+ std::cout << "mean value of basin #" << i << " is
" << m(i) << std::endl;
- level::fill(cell, level::transform(label, m));
+ level::fill(cell, level::transform(lab, m));
debug::println(cell);
// 2 2 2
//
// 5 5 5
- // DONE!
- */
+ // DONE!
}
Index: mln/core/site_set/all.hh
--- mln/core/site_set/all.hh (revision 2280)
+++ mln/core/site_set/all.hh (working copy)
@@ -31,18 +31,24 @@
/*! \file mln/core/site_set/all.hh
*
* \brief File that includes all site_set types.
- *
- * \todo Make it effective after having moved image-defining files.
*/
-// # include <mln/core/site_set/p_array_of.hh> // FIXME: Uncomment.
+# include <mln/core/site_set/box.hh>
+# include <mln/core/site_set/line2d.hh>
+# include <mln/core/site_set/p_array.hh>
+# include <mln/core/site_set/p_centered.hh>
+# include <mln/core/site_set/p_if.hh>
# include <mln/core/site_set/p_image.hh>
# include <mln/core/site_set/p_key.hh>
# include <mln/core/site_set/p_mutable_array_of.hh>
+# include <mln/core/site_set/p_priority.hh>
+# include <mln/core/site_set/p_queue.hh>
+# include <mln/core/site_set/p_queue_fast.hh>
+# include <mln/core/site_set/p_run.hh>
+# include <mln/core/site_set/p_set.hh>
# include <mln/core/site_set/p_set_of.hh>
# include <mln/core/site_set/p_vaccess.hh>
-// FIXME: Complete...
#endif // ! MLN_CORE_SITE_SET_ALL_HH
Index: mln/core/site_set/p_centered.hh
--- mln/core/site_set/p_centered.hh (revision 0)
+++ mln/core/site_set/p_centered.hh (revision 0)
@@ -0,0 +1,300 @@
+// 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
+// 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_CORE_SITE_SET_P_CENTERED_HH
+# define MLN_CORE_SITE_SET_P_CENTERED_HH
+
+/*! \file mln/core/site_set/p_centered.hh
+ *
+ * \brief This file defines the site set corresponding to a window
+ * centered on a site.
+ *
+ * \todo Add the bkd iter.
+ * \todo Code is_valid() and change_target() for the site set.
+ */
+
+# include <mln/core/internal/site_set_base.hh>
+
+
+namespace mln
+{
+
+ // Fwd decls.
+ template <typename W> class p_centered;
+ template <typename W> class p_centered_piter;
+
+
+ namespace trait
+ {
+
+ template <typename W>
+ struct site_set_< p_centered<W> >
+ {
+ typedef trait::site_set::nsites::unknown nsites;
+ typedef trait::site_set::bbox::unknown bbox;
+ typedef trait::site_set::contents::fixed contents;
+ typedef trait::site_set::arity::unique arity;
+ };
+
+// template <typename W>
+// struct set_precise_unary_< op::ord, p_centered<W> >
+// {
+// typedef set_precise_unary_< op::ord, p_centered<W> > ret; //
Itself.
+// bool strict(const p_centered<W>& lhs, const p_centered<W>&
rhs) const;
+// };
+
+ } // end of namespace mln::trait
+
+
+ template <typename W>
+ class p_centered : public internal::site_set_base_< mln_psite(W),
p_centered<W> >,
+ private mlc_is_a(W, Window)::check_t
+ {
+ public:
+
+ /// Psite associated type.
+ typedef mln_psite(W) psite;
+
+ /// Site associated type.
+ typedef mln_site(W) site;
+
+
+ /// Element associated type.
+ typedef psite element;
+
+
+ /// Forward Site_Iterator associated type.
+ typedef p_centered_piter<W> fwd_piter;
+
+ /// Backward Site_Iterator associated type.
+ typedef p_centered_piter<W> bkd_piter; // FIXME
+
+ /// Site_Iterator associated type.
+ typedef fwd_piter piter;
+
+
+ /// Constructor without argument.
+ p_centered();
+
+ /// Constructor from a window \p win and a center \p c.
+ p_centered(const W& win, const mln_psite(W)& c);
+
+
+ /// Test if \p p belongs to the box.
+ template <typename P>
+ bool has(const P& p) const;
+
+ /// Test if this site set is initialized.
+ bool is_valid() const;
+
+ /// Return the size of this site set in memory.
+ std::size_t memory_size() const;
+
+ /// Give the center of this site set.
+ const mln_psite(W)& center() const;
+
+ /// Give the window this site set is defined upon.
+ const W& window() const;
+
+ protected:
+
+ W win_;
+ mln_psite(W) c_;
+ };
+
+
+ template <typename W>
+ class p_centered_piter : public internal::site_set_iterator_base<
p_centered<W>,
+ p_centered_piter<W> >
+ {
+ typedef p_centered_piter<W> self_;
+ typedef internal::site_set_iterator_base< p_centered<W>, self_ > super_;
+ public:
+
+ /// Constructor without argument.
+ p_centered_piter();
+
+ /// Constructor.
+ p_centered_piter(const p_centered<W>& s);
+
+ /// Test the iterator validity.
+ bool is_valid_() const;
+
+ /// Invalidate the iterator.
+ void invalidate_();
+
+ /// Start an iteration.
+ void start_();
+
+ /// Go to the next point.
+ void next_();
+
+ protected:
+ using super_::p_;
+ using super_::s_;
+
+ mln_fwd_qiter(W) q_;
+ };
+
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ // p_centered<W>
+
+ template <typename W>
+ inline
+ bool
+ p_centered<W>::is_valid() const
+ {
+ return true; // FIXME
+ }
+
+ template <typename W>
+ inline
+ p_centered<W>::p_centered()
+ {
+ }
+
+ template <typename W>
+ inline
+ p_centered<W>::p_centered(const W& win, const mln_psite(W)& c)
+ : win_(win),
+ c_(c)
+ {
+ mln_precondition(is_valid());
+ }
+
+ template <typename W>
+ template <typename P>
+ inline
+ bool
+ p_centered<W>::has(const P&) const
+ {
+ mln_precondition(is_valid());
+ return true; // FIXME
+ }
+
+ template <typename W>
+ inline
+ std::size_t
+ p_centered<W>::memory_size() const
+ {
+ return sizeof(*this);
+ }
+
+ template <typename W>
+ inline
+ const mln_psite(W)&
+ p_centered<W>::center() const
+ {
+ return c_;
+ }
+
+ template <typename W>
+ inline
+ const W&
+ p_centered<W>::window() const
+ {
+ return win_;
+ }
+
+// namespace trait
+// {
+
+// template <typename W>
+// inline
+// bool
+// set_precise_unary_< op::ord, p_centered<W> >::strict(const
p_centered<W>& lhs, const p_centered<W>& rhs) const
+// {
+// // Lexicographical over "pmin then pmax".
+// return util::ord_lexi_strict(lhs.pmin(), lhs.pmax(),
+// rhs.pmin(), rhs.pmax());
+// }
+
+// } // end of namespace mln::trait
+
+
+ // p_centered_piter<W>
+
+ template <typename W>
+ inline
+ p_centered_piter<W>::p_centered_piter()
+ {
+ }
+
+ template <typename W>
+ inline
+ p_centered_piter<W>::p_centered_piter(const p_centered<W>& s)
+ {
+ this->change_target(s);
+ q_.center_at(s.center());
+ q_.change_target(s.window());
+ }
+
+ template <typename W>
+ inline
+ bool
+ p_centered_piter<W>::is_valid_() const
+ {
+ return q_.is_valid();
+ }
+
+ template <typename W>
+ inline
+ void
+ p_centered_piter<W>::invalidate_()
+ {
+ q_.invalidate();
+ }
+
+ template <typename W>
+ inline
+ void
+ p_centered_piter<W>::start_()
+ {
+ q_.start();
+ if (is_valid_())
+ p_ = q_;
+ }
+
+ template <typename W>
+ inline
+ void
+ p_centered_piter<W>::next_()
+ {
+ q_.next();
+ if (is_valid_())
+ p_ = q_;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+} // end of namespace mln
+
+
+#endif // ! MLN_CORE_SITE_SET_P_CENTERED_HH
Index: mln/core/image/extension_fun.hh
--- mln/core/image/extension_fun.hh (revision 2280)
+++ mln/core/image/extension_fun.hh (working copy)
@@ -35,10 +35,10 @@
* with a function.
*
* \todo Deal with two-ways functions...
+ * \todo Use an envelop as lvalue to test extension writing.
*/
# include <mln/core/internal/image_identity.hh>
-# include <mln/metal/converts_to.hh>
@@ -81,6 +81,15 @@
typedef trait::image::ext_io::read_only ext_io;
};
+ template <typename I, typename F, typename V>
+ struct ch_value< extension_fun<I, F>, V >
+ {
+ typedef mlc_converts_to(mln_result(F), V) keep_ext;
+ typedef mln_ch_value(I, V) Iv;
+ typedef extension_fun<Iv, F> Iv_ext;
+ typedef mlc_if(keep_ext, Iv_ext, Iv) ret;
+ };
+
} // end of namespace mln::trait
Index: mln/core/image/extended.hh
--- mln/core/image/extended.hh (revision 0)
+++ mln/core/image/extended.hh (revision 0)
@@ -0,0 +1,226 @@
+// 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_CORE_IMAGE_EXTENDED_HH
+# define MLN_CORE_IMAGE_EXTENDED_HH
+
+/*!
+ * \file mln/core/image/extended.hh
+ *
+ * \brief Definition of morpher that makes an image become restricted
+ * given by a point set.
+ *
+ * \todo Add a special case for "ima | box"; think about some other
+ * special cases...
+ */
+
+# include <mln/core/internal/image_domain_morpher.hh>
+# include <mln/core/site_set/box.hh>
+
+
+namespace mln
+{
+
+
+ // Forward declaration.
+ template <typename I> class extended;
+
+
+ namespace internal
+ {
+
+ /// Data structure for \c mln::extended<I>.
+ template <typename I>
+ struct data< extended<I> >
+ {
+ data(I& ima, const box<mln_site(I)>& b_);
+
+ I ima_;
+ box<mln_site(I)> b_;
+ };
+
+ } // end of namespace mln::internal
+
+
+
+ namespace trait
+ {
+
+ template <typename I>
+ struct image_< extended<I> > : default_image_morpher< I,
+ mln_value(I),
+ extended<I> >
+ {
+ typedef trait::image::category::domain_morpher category;
+
+ typedef trait::image::ext_domain::none ext_domain;
+ typedef trait::image::ext_value::irrelevant ext_value;
+ typedef trait::image::ext_io::irrelevant ext_io;
+
+ typedef trait::image::value_storage::disrupted value_storage;
+ };
+
+ } // end of namespace mln::trait
+
+
+
+ // FIXME: Doc!
+
+ template <typename I>
+ struct extended : public internal::image_domain_morpher< I,
+ box<mln_site(I)>,
+ extended<I> >,
+ private mlc_not_equal(mln_trait_image_ext_domain(I),
+ trait::image::ext_domain::none)::check_t
+ {
+ /// Skeleton.
+ typedef tag::image_<I> skeleton; // This property is lost!
+
+ /// Constructor without argument.
+ extended();
+
+ /// Constructor.
+ extended(I& ima, const box<mln_site(I)>& );
+
+ /// Initialization.
+ void init_(I& ima, const box<mln_site(I)>& b);
+
+ /// Give the definition domain.
+ const box<mln_site(I)>& domain() const;
+ };
+
+
+
+ template <typename I, typename J>
+ void init_(tag::image_t, extended<I>& target, const J& model);
+
+
+ template <typename I, typename B>
+ extended<const I>
+ extended_to(const Image<I>& ima, const Box<B>& b);
+
+ template <typename I, typename B>
+ extended<I>
+ extended_to(Image<I>& ima, const Box<B>& b);
+
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ // init_
+
+ template <typename I, typename J>
+ inline
+ void init_(tag::image_t, extended<I>& target, const J& model)
+ {
+ I ima;
+ init_(tag::image, ima, model);
+ box<mln_site(I)> b;
+ init_(tag::bbox, b, model);
+ target.init_(ima, b);
+ }
+
+
+ // internal::data< extended<I> >
+
+ namespace internal
+ {
+
+ template <typename I>
+ inline
+ data< extended<I> >::data(I& ima, const box<mln_site(I)>&
b)
+ : ima_(ima),
+ b_(b)
+ {
+ }
+
+ } // end of namespace mln::internal
+
+
+ // extended<I>
+
+ template <typename I>
+ inline
+ extended<I>::extended()
+ {
+ }
+
+ template <typename I>
+ inline
+ extended<I>::extended(I& ima, const box<mln_site(I)>& b)
+ {
+ init_(ima, b);
+ }
+
+ template <typename I>
+ inline
+ void
+ extended<I>::init_(I& ima, const box<mln_site(I)>& b)
+ {
+ mln_precondition(! this->has_data());
+ this->data_ = new internal::data< extended<I> >(ima, b);
+ }
+
+ template <typename I>
+ inline
+ const box<mln_site(I)>&
+ extended<I>::domain() const
+ {
+ return this->data_->b_;
+ }
+
+
+ // extended_to
+
+ template <typename I, typename B>
+ extended<const I>
+ extended_to(const Image<I>& ima, const Box<B>& b)
+ {
+ mlc_not_equal(mln_trait_image_ext_domain(I),
+ trait::image::ext_domain::none)::check();
+ mln_precondition(exact(ima).has_data());
+ extended<const I> tmp(exact(ima), exact(b));
+ return tmp;
+ }
+
+ template <typename I, typename B>
+ extended<I>
+ extended_to(Image<I>& ima, const Box<B>& b)
+ {
+ mlc_not_equal(mln_trait_image_ext_domain(I),
+ trait::image::ext_domain::none)::check();
+ mln_precondition(exact(ima).has_data());
+ extended<I> tmp(exact(ima), exact(b));
+ return tmp;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+} // end of namespace mln
+
+
+#endif // ! MLN_CORE_IMAGE_EXTENDED_HH
Index: mln/core/image/extension_ima.hh
--- mln/core/image/extension_ima.hh (revision 2280)
+++ mln/core/image/extension_ima.hh (working copy)
@@ -35,10 +35,10 @@
* with a function.
*
* \todo Use the 'instant' mechanism.
+ * \todo Use an envelop as lvalue to test extension writing.
*/
# include <mln/core/internal/image_identity.hh>
-# include <mln/metal/converts_to.hh>
@@ -81,6 +81,15 @@
typedef mln_trait_image_value_io(J) ext_io;
};
+ template <typename I, typename J, typename V>
+ struct ch_value< extension_ima<I, J>, V >
+ {
+ typedef mlc_converts_to(mln_result(J), V) keep_ext;
+ typedef mln_ch_value(I, V) Iv;
+ typedef extension_ima<Iv, J> Iv_ext;
+ typedef mlc_if(keep_ext, Iv_ext, Iv) ret;
+ };
+
} // end of namespace mln::trait
Index: mln/core/image/image1d.hh
--- mln/core/image/image1d.hh (revision 2280)
+++ mln/core/image/image1d.hh (working copy)
@@ -39,7 +39,6 @@
# include <mln/value/set.hh>
# include <mln/fun/i2v/all_to.hh>
-# include <mln/core/line_piter.hh>
// FIXME:
Index: mln/core/image/image3d.hh
--- mln/core/image/image3d.hh (revision 2280)
+++ mln/core/image/image3d.hh (working copy)
@@ -40,7 +40,7 @@
# include <mln/value/set.hh>
# include <mln/fun/i2v/all_to.hh>
-# include <mln/core/line_piter.hh>
+// # include <mln/core/line_piter.hh>
// FIXME:
@@ -131,7 +131,7 @@
typedef dpoint3d dpoint;
typedef mln_fwd_piter(box3d) fwd_piter;
typedef mln_bkd_piter(box3d) bkd_piter;
- typedef line_piter_<point> line_piter;
+// typedef line_piter_<point> line_piter;
// End of warning.
Index: mln/core/image/extension_val.hh
--- mln/core/image/extension_val.hh (revision 2280)
+++ mln/core/image/extension_val.hh (working copy)
@@ -34,10 +34,10 @@
* \brief Definition of a morpher that extends the domain of an image.
*
* \todo Use the 'instant' mechanism.
+ * \todo Use an envelop as lvalue to test extension writing.
*/
# include <mln/core/internal/image_identity.hh>
-# include <mln/metal/converts_to.hh>
@@ -80,6 +80,15 @@
typedef trait::image::ext_io::read_write ext_io;
};
+ template <typename I, typename V>
+ struct ch_value< extension_val<I>, V >
+ {
+ typedef mlc_converts_to(mln_value(I), V) keep_ext;
+ typedef mln_ch_value(I, V) Iv;
+ typedef extension_val<Iv> Iv_ext;
+ typedef mlc_if(keep_ext, Iv_ext, Iv) ret;
+ };
+
} // end of namespace mln::trait
Index: mln/core/point.hh
--- mln/core/point.hh (revision 2280)
+++ mln/core/point.hh (working copy)
@@ -140,7 +140,7 @@
/// \{ Constructors with different numbers of arguments
/// (coordinates) w.r.t. the dimension.
- point(C ind);
+ explicit point(C ind);
point(C row, C col);
point(C sli, C row, C col);
/// \}
Index: mln/level/sort_psites.hh
--- mln/level/sort_psites.hh (revision 2280)
+++ mln/level/sort_psites.hh (working copy)
@@ -38,6 +38,7 @@
# include <mln/core/concept/image.hh>
# include <mln/convert/to_p_array.hh>
# include <mln/histo/compute.hh>
+# include <mln/util/ord.hh>
namespace mln
@@ -89,8 +90,10 @@
bool operator()(const mln_psite(I)& lhs,
const mln_psite(I)& rhs) const
{
- return ima_(lhs) < ima_(rhs) || (ima_(lhs) == ima_(rhs)
- && lhs < rhs);
+ return util::ord_strict(ima_(lhs), ima_(rhs))
+ || (ima_(lhs) == ima_(rhs)
+ &&
+ util::ord_strict(lhs, rhs));
}
};
@@ -109,8 +112,10 @@
bool operator()(const mln_psite(I)& lhs,
const mln_psite(I)& rhs) const
{
- return ima_(lhs) > ima_(rhs) || (ima_(lhs) == ima_(rhs)
- && lhs > rhs);
+ return util::ord_strict(ima_(rhs), ima_(lhs))
+ || (ima_(lhs) == ima_(rhs)
+ &&
+ util::ord_strict(rhs, lhs));
}
};
Index: mln/border/fill.hh
--- mln/border/fill.hh (revision 2280)
+++ mln/border/fill.hh (working copy)
@@ -77,12 +77,12 @@
for_all (pl)
{
std::size_t end = ima.index_of_point (pl);
- std::memset((void*)&ima[st],
+ std::memset((void*)&ima.element(st),
*(const int*)(&v),
end - st);
st = end + len_r;
}
- std::memset((void*)&ima[st],
+ std::memset((void*)&ima.element(st),
*(const int*)(&v),
ima.nelements () - st);
Index: mln/border/mirror.hh
--- mln/border/mirror.hh (revision 2280)
+++ mln/border/mirror.hh (working copy)
@@ -73,9 +73,10 @@
template <typename I>
inline
- void mirror_(const box1d&, const I& ima)
+ void mirror_(const box1d&, const I& ima_)
{
trace::entering("border::impl::mirror_");
+ I& ima = const_cast<I&>(ima_);
std::size_t border = ima.border ();
std::size_t nbinds = geom::ninds(ima);
@@ -90,10 +91,10 @@
{
std::size_t i = 0;
for (; i < min; ++i)
- const_cast<I&>(ima)[border - 1 - i] = ima(point1d(i));
+ ima.element(border - 1 - i) = ima(point1d(i));
for (; i < border; ++i)
- const_cast<I&>(ima)[border - 1 - i] = ima(point1d(min - 1));
+ ima.element(border - 1 - i) = ima(point1d(min - 1));
}
/// right border
@@ -103,21 +104,22 @@
for (;
i < min;
++i, --j)
- const_cast<I&>(ima)[border + nbinds + i] = ima(point1d(j));
+ ima.element(border + nbinds + i) = ima(point1d(j));
++j;
for (;
i < border;
++i)
- const_cast<I&>(ima)[border + nbinds + i] = ima(point1d(j));
+ ima.element(border + nbinds + i) = ima(point1d(j));
}
trace::exiting("border::impl::mirror_");
}
template <typename I>
inline
- void mirror_(const box2d&, const I& ima)
+ void mirror_(const box2d&, const I& ima_)
{
trace::entering("border::impl::mirror_");
+ I& ima = const_cast<I&>(ima_);
std::size_t border = ima.border ();
std::size_t nbrows = geom::max_row(ima) - geom::min_row(ima);
@@ -129,49 +131,49 @@
// mirror top left corner
for (std::size_t i = 0; i < border; ++i)
for (std::size_t j = 0; j < border; ++j)
- const_cast<I&>(ima)[i * ((nbcols + 1) + 2 * border) + j] = ima[s];
+ ima.element(i * ((nbcols + 1) + 2 * border) + j) = ima.element(s);
// mirror top left corner
s = start + nbcols;
for (std::size_t i = 0; i < border; ++i)
for (std::size_t j = 1; j <= border; ++j)
- const_cast<I&>(ima)[i * ((nbcols + 1) + 2 * border) + (nbcols + border +
j)] = ima[s];
+ ima.element(i * ((nbcols + 1) + 2 * border) + (nbcols + border + j)) =
ima.element(s);
// mirror bottom left corner
s = start + (nbrows * real_nbcols);
for (std::size_t i = 1; i <= border; ++i)
for (std::size_t j = 1; j <= border; ++j)
- const_cast<I&>(ima)[s - i + (j * (real_nbcols))] = ima[s];
+ ima.element(s - i + (j * (real_nbcols))) = ima.element(s);
// mirror bottom right corner
s = start + (nbrows * real_nbcols) + nbcols;
for (std::size_t i = 1; i <= border; ++i)
for (std::size_t j = 1; j <= border; ++j)
- const_cast<I&>(ima)[s + i + (j * real_nbcols)] = ima[s];
+ ima.element(s + i + (j * real_nbcols)) = ima.element(s);
// mirror top border
s = start;
for (std::size_t i = 0; i <= nbcols; ++i)
for (std::size_t j = 1; j <= border; ++j)
- const_cast<I&>(ima)[s + i - (j * real_nbcols)] = ima[s + i + ((j - 1)*
real_nbcols)];
+ ima.element(s + i - (j * real_nbcols)) = ima.element(s + i + ((j - 1)*
real_nbcols));
// mirror left border
s = start;
for (std::size_t i = 0; i <= nbrows; ++i)
for (std::size_t j = 1; j <= border; ++j)
- const_cast<I&>(ima)[s + (i * real_nbcols) - j] = ima[s + (i * real_nbcols)
+ (j - 1)];
+ ima.element(s + (i * real_nbcols) - j) = ima.element(s + (i * real_nbcols) + (j -
1));
// mirror right border
s = start;
for (std::size_t i = 0; i <= nbrows; ++i)
for (std::size_t j = 1; j <= border; ++j)
- const_cast<I&>(ima)[s + (i * real_nbcols + nbcols) + j] = ima[s + (i *
real_nbcols + nbcols) - (j - 1)];
+ ima.element(s + (i * real_nbcols + nbcols) + j) = ima.element(s + (i * real_nbcols +
nbcols) - (j - 1));
// mirror bottom border
s = start + (nbrows * real_nbcols);
for (std::size_t i = 0; i <= nbcols; ++i)
for (std::size_t j = 1; j <= border; ++j)
- const_cast<I&>(ima)[s + i + (j * real_nbcols)] = ima[s + i - ((j - 1)*
real_nbcols)];
+ ima.element(s + i + (j * real_nbcols)) = ima.element(s + i - ((j - 1)*
real_nbcols));
trace::exiting("border::impl::mirror_");
}
Index: mln/fun/i2v/array.hh
--- mln/fun/i2v/array.hh (revision 0)
+++ mln/fun/i2v/array.hh (revision 0)
@@ -0,0 +1,147 @@
+// 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_FUN_I2V_ARRAY_HH
+# define MLN_FUN_I2V_ARRAY_HH
+
+/*! \file mln/fun/i2v/array.hh
+ *
+ * \brief FIXME.
+ */
+
+# include <vector>
+# include <algorithm>
+# include <mln/core/concept/function.hh>
+
+
+namespace mln
+{
+
+ namespace fun
+ {
+
+ namespace i2v
+ {
+
+ template <typename T>
+ class array : public Function_i2v< array<T> >
+ {
+ public:
+
+ typedef T result;
+
+ array();
+ array(unsigned n);
+
+ void resize(unsigned n);
+ unsigned size() const;
+
+ T operator()(unsigned i) const;
+ T& operator()(unsigned i);
+
+ private:
+ std::vector<T> v_;
+ };
+
+ } // end of namespace mln::fun::i2v
+
+ } // end of namespace mln::fun
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ namespace fun
+ {
+
+ namespace i2v
+ {
+
+ template <typename T>
+ inline
+ array<T>::array()
+ {
+ }
+
+ template <typename T>
+ inline
+ array<T>::array(unsigned n)
+ {
+ resize(n);
+ }
+
+ template <typename T>
+ inline
+ void
+ array<T>::resize(unsigned n)
+ {
+ v_.resize(n);
+ }
+
+ template <typename T>
+ inline
+ unsigned
+ array<T>::size() const
+ {
+ return v_.size();
+ }
+
+ template <typename T>
+ inline
+ T
+ array<T>::operator()(unsigned i) const
+ {
+ mln_precondition(i < v_.size());
+ return v_[i];
+ }
+
+ template <typename T>
+ inline
+ T&
+ array<T>::operator()(unsigned i)
+ {
+ mln_precondition(i < v_.size());
+ return v_[i];
+ }
+
+ } // end of namespace mln::fun::i2v
+
+ } // end of namespace mln::fun
+
+ template <typename T>
+ inline
+ fun::i2v::array<T> array(T t)
+ {
+ fun::i2v::array<T> tmp(t);
+ return tmp;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+} // end of namespace mln
+
+
+#endif // ! MLN_FUN_I2V_ARRAY_HH
Index: mln/win/all.hh
--- mln/win/all.hh (revision 2280)
+++ mln/win/all.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
@@ -44,10 +44,12 @@
# include <mln/win/backdiag2d.hh>
# include <mln/win/cube3d.hh>
+# include <mln/win/cuboid3d.hh>
# include <mln/win/diag2d.hh>
# include <mln/win/disk2d.hh>
# include <mln/win/hline2d.hh>
# include <mln/win/line.hh>
+# include <mln/win/multiple.hh>
# include <mln/win/octagon2d.hh>
# include <mln/win/rectangle2d.hh>
# include <mln/win/segment1d.hh>
Index: mln/win/multiple.hh
--- mln/win/multiple.hh (revision 2280)
+++ mln/win/multiple.hh (working copy)
@@ -119,7 +119,7 @@
mln_psite(W) compute_p_() const;
private:
- int i_;
+ unsigned i_;
unsigned n_() const;
};