https://svn.lrde.epita.fr/svn/oln/trunk/milena
Index: ChangeLog
from Thierry Geraud <thierry.geraud(a)lrde.epita.fr>
Add area opening over its new canvas.
* tests/morpho_opening_area.cc: New.
* mln/core/concept/accumulator.hh (take_as_init): New.
* mln/morpho/opening_attribute.hh: New.
* mln/morpho/opening_area.hh: New.
* mln/morpho/includes.hh: Add neighborhood.hh.
* mln/canvas/morpho: New.
* mln/canvas/morpho/algebraic_union_find.hh: New.
* mln/accu/count.hh (result): New.
* mln/util: New.
* mln/util/pix.hh: New.
mln/accu/count.hh | 9 +
mln/canvas/morpho/algebraic_union_find.hh | 173 ++++++++++++++++++++++++++++++
mln/core/concept/accumulator.hh | 14 ++
mln/morpho/includes.hh | 1
mln/morpho/opening_area.hh | 71 ++++++++++++
mln/morpho/opening_attribute.hh | 135 +++++++++++++++++++++++
mln/util/pix.hh | 106 ++++++++++++++++++
tests/morpho_opening_area.cc | 55 +++++++++
8 files changed, 564 insertions(+)
Index: tests/morpho_opening_area.cc
--- tests/morpho_opening_area.cc (revision 0)
+++ tests/morpho_opening_area.cc (revision 0)
@@ -0,0 +1,55 @@
+// Copyright (C) 2007 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.
+
+/*! \file tests/morpho_opening_area.cc
+ *
+ * \brief Test on mln::morpho::opening_area.
+ */
+
+#include <mln/core/image2d_b.hh>
+#include <mln/value/int_u8.hh>
+#include <mln/core/neighb2d.hh>
+
+#include <mln/io/load_pgm.hh>
+#include <mln/io/save_pgm.hh>
+
+#include <mln/morpho/opening_area.hh>
+
+
+
+int main()
+{
+ using namespace mln;
+ using value::int_u8;
+
+ image2d_b<int_u8>
+ lena = io::load_pgm("../img/lena.pgm"),
+ out(lena.domain());
+
+ morpho::opening_area(lena, c4(), 510, out);
+ io::save_pgm(out, "out.pgm");
+}
Index: mln/core/concept/accumulator.hh
--- mln/core/concept/accumulator.hh (revision 1087)
+++ mln/core/concept/accumulator.hh (working copy)
@@ -56,6 +56,11 @@
void take(const value& v);
void take(const E& other);
*/
+
+ // Default impl.
+ template <typename T>
+ void take_as_init(const T& t); // 't' is either value or E.
+
protected:
Accumulator();
};
@@ -90,6 +95,15 @@
}
template <typename E>
+ template <typename T>
+ void
+ Accumulator<E>::take_as_init(const T& t) // either value or E
+ {
+ exact(this)->init();
+ exact(this)->take(t);
+ }
+
+ template <typename E>
E merge(const Accumulator<E>& lhs, const Accumulator<E>& rhs)
{
E tmp(exact(lhs));
Index: mln/morpho/opening_attribute.hh
--- mln/morpho/opening_attribute.hh (revision 0)
+++ mln/morpho/opening_attribute.hh (revision 0)
@@ -0,0 +1,135 @@
+// Copyright (C) 2007 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_MORPHO_OPENING_ATTRIBUTE_HH
+# define MLN_MORPHO_OPENING_ATTRIBUTE_HH
+
+/*! \file mln/morpho/opening_attribute.hh
+ *
+ * \brief Morphological attribute opening.
+ */
+
+# include <mln/morpho/includes.hh>
+# include <mln/canvas/morpho/algebraic_union_find.hh>
+# include <mln/level/sort_points.hh>
+
+
+namespace mln
+{
+
+ namespace morpho
+ {
+
+ /*! Morphological area opening.
+ */
+ template <typename A,
+ typename I, typename N, typename O>
+ void opening_attribute(const Image<I>& input, const Neighborhood<N>& nbh, mln_result(A) lambda,
+ Image<O>& output);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ namespace impl
+ {
+
+ template <typename A_,
+ typename I_, typename N_, typename O_>
+ struct opening_attribute_t
+ {
+ typedef mln_point(I_) P;
+
+ // requirements from mln::canvas::morpho::algebraic_union_find
+
+ typedef A_ A;
+ typedef I_ I;
+ typedef N_ N;
+ typedef O_ O;
+ typedef vec_p<P> S;
+ typedef util::pix_<I> pix_t;
+
+ const I& input;
+ const N& nbh;
+ mln_result(A) lambda;
+ O& output;
+
+ const S s;
+
+ void init()
+ {
+ // FIXME: border::fill(input, mln_max(mln_value(I)));
+ }
+
+ bool is_active(const A& attr) const
+ {
+ return attr.to_value() < lambda;
+ }
+
+ void inactivate(A& attr)
+ {
+ attr.set_value(lambda);
+ }
+
+ // end of requirements
+
+ opening_attribute_t(const I_& input, const N_& nbh, mln_result(A) lambda, O_& output)
+ : input(input), nbh(nbh), lambda(lambda), output(output),
+ s(level::sort_points_decreasing(input))
+ {
+ }
+
+ };
+
+ } // end of namespace mln::morpho::impl
+
+
+ template <typename A,
+ typename I, typename N, typename O>
+ void opening_attribute(const Image<I>& input_,
+ const Neighborhood<N>& nbh_, mln_result(A) lambda,
+ Image<O>& output_)
+ {
+ const I& input = exact(input_);
+ const N& nbh = exact(nbh_);
+ O& output = exact(output_);
+ mln_precondition(output.domain() = input.domain());
+
+ typedef impl::opening_attribute_t<A,I,N,O> F;
+ F f(input, nbh, lambda, output);
+ canvas::morpho::algebraic_union_find<F> run(f);
+
+ mln_postcondition(output <= input);
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace mln::morpho
+
+} // end of namespace mln
+
+
+#endif // ! MLN_MORPHO_OPENING_ATTRIBUTE_HH
Index: mln/morpho/opening_area.hh
--- mln/morpho/opening_area.hh (revision 0)
+++ mln/morpho/opening_area.hh (revision 0)
@@ -0,0 +1,71 @@
+// Copyright (C) 2007 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_MORPHO_OPENING_AREA_HH
+# define MLN_MORPHO_OPENING_AREA_HH
+
+/*! \file mln/morpho/opening_area.hh
+ *
+ * \brief Morphological area opening.
+ */
+
+# include <mln/morpho/opening_attribute.hh>
+# include <mln/accu/count.hh>
+
+
+namespace mln
+{
+
+ namespace morpho
+ {
+
+ /*! Morphological area opening.
+ */
+ template <typename I, typename N, typename O>
+ void opening_area(const Image<I>& input, const Neighborhood<N>& nbh, std::size_t lambda,
+ Image<O>& output);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename I, typename N, typename O>
+ void opening_area(const Image<I>& input, const Neighborhood<N>& nbh, std::size_t lambda,
+ Image<O>& output)
+ {
+ mln_precondition(exact(output).domain() = exact(input).domain());
+ typedef util::pix_<I> pix_t;
+ opening_attribute< accu::count<pix_t> >(input, nbh, lambda, output);
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace mln::morpho
+
+} // end of namespace mln
+
+
+#endif // ! MLN_MORPHO_OPENING_AREA_HH
Index: mln/morpho/includes.hh
--- mln/morpho/includes.hh (revision 1087)
+++ mln/morpho/includes.hh (working copy)
@@ -36,6 +36,7 @@
# include <mln/core/concept/image.hh>
# include <mln/core/concept/window.hh>
+# include <mln/core/concept/neighborhood.hh>
# include <mln/accu/min.hh>
# include <mln/accu/max.hh>
Index: mln/canvas/morpho/algebraic_union_find.hh
--- mln/canvas/morpho/algebraic_union_find.hh (revision 0)
+++ mln/canvas/morpho/algebraic_union_find.hh (revision 0)
@@ -0,0 +1,173 @@
+// Copyright (C) 2007 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_CANVAS_MORPHO_ALGEBRAIC_UNION_FIND_HH
+# define MLN_CANVAS_MORPHO_ALGEBRAIC_UNION_FIND_HH
+
+/*! \file mln/canvas/morpho/algebraic_union_find.hh
+ *
+ * \brief FIXME: Doc!
+ */
+
+# include <mln/core/concept/image.hh>
+# include <mln/core/concept/neighborhood.hh>
+# include <mln/level/fill.hh>
+# include <mln/util/pix.hh>
+
+
+namespace mln
+{
+
+ namespace canvas
+ {
+
+ namespace morpho
+ {
+
+ // General version.
+
+ template <typename F>
+ struct algebraic_union_find
+ {
+ F& f;
+
+ typedef typename F::I I;
+ typedef typename F::N N;
+ typedef typename F::O O;
+ typedef typename F::S S;
+ typedef typename F::A A;
+ typedef mln_point(I) point;
+
+ // aux:
+ mln_ch_value(O, bool) deja_vu;
+ mln_ch_value(O, point) parent;
+ mln_ch_value(O, A) data;
+
+ algebraic_union_find(F& f)
+ : f(f),
+ deja_vu(f.output.domain()),
+ parent(f.output.domain()),
+ data(f.output.domain())
+ {
+ run();
+ }
+
+ void run()
+ {
+ // init
+ {
+ mln::level::fill(deja_vu, false);
+ f.init();
+ }
+ // first pass
+ {
+ mln_fwd_piter(S) p(f.s);
+ mln_niter(N) n(f.nbh, p);
+ for_all(p)
+ {
+ make_set(p);
+ for_all(n)
+ if (f.input.has(n) && deja_vu(n))
+ do_union(n, p);
+ deja_vu(p) = true;
+ }
+ }
+
+ // second pass
+ {
+ mln_bkd_piter(S) p(f.s);
+ mln_niter(N) n(f.nbh, p);
+ for_all(p)
+ if (is_root(p))
+ f.output(p) = f.input(p);
+ else
+ f.output(p) = f.output(parent(p));
+ }
+
+ /*
+ Change 2nd pass into:
+ for_all(p) if (not is_root(p)) f.output(p) = f.output(parent(p));
+ and add in init:
+ mln::level::assign(f.output, f.input);
+ */
+
+ } // end of run()
+
+ void make_set(const point& p)
+ {
+ parent(p) = p;
+ data(p).take_as_init(util::pix(f.input, p));
+ }
+
+ bool is_root(const point& p) const
+ {
+ return parent(p) = p;
+ }
+
+ point find_root(const point& x)
+ {
+ if (parent(x) = x)
+ return x;
+ else
+ return parent(x) = find_root(parent(x));
+ }
+
+ bool equiv(const point2d& r, const point2d& p)
+ {
+ // Either a flat zone or the component of r is still growing.
+ return f.input(r) = f.input(p) || f.is_active(data(r));
+ }
+
+ void do_union(const point& n, const point& p)
+ {
+ point r = find_root(n);
+ if (r != p)
+ {
+ if (equiv(r, p))
+ {
+ data(p).take(data(r));
+ parent(r) = p;
+ }
+ else
+ f.inactivate(data(p));
+ }
+ }
+
+ };
+
+
+ // FIXME: Fast version.
+
+
+ } // end of namespace mln::canvas::morpho
+
+ } // end of namespace mln::canvas
+
+} // end of namespace mln
+
+
+#endif // ! MLN_CANVAS_MORPHO_ALGEBRAIC_UNION_FIND_HH
Index: mln/accu/count.hh
--- mln/accu/count.hh (revision 1087)
+++ mln/accu/count.hh (working copy)
@@ -49,6 +49,7 @@
struct count : public Accumulator< count<V> >
{
typedef V value;
+ typedef std::size_t result; // FIXME: Up in Accumulator.
count();
@@ -57,6 +58,7 @@
void take(const count<V>& other);
std::size_t to_value() const;
+ void set_value(std::size_t c);
protected:
@@ -101,6 +103,13 @@
return count_;
}
+ template <typename V>
+ void
+ count<V>::set_value(std::size_t c)
+ {
+ count_ = c;
+ }
+
# endif // ! MLN_INCLUDE_ONLY
} // end of namespace mln::accu
Index: mln/util/pix.hh
--- mln/util/pix.hh (revision 0)
+++ mln/util/pix.hh (revision 0)
@@ -0,0 +1,106 @@
+// Copyright (C) 2007 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_UTIL_PIX_HH
+# define MLN_UTIL_PIX_HH
+
+/*! \file mln/util/pix.hh
+ *
+ * \brief Definition of an instant pix.
+ */
+
+# include <mln/core/concept/image.hh>
+
+
+namespace mln
+{
+
+ namespace util
+ {
+
+ /// Pix structure.
+ template <typename I>
+ struct pix_
+ {
+ pix_(const Image<I>& ima, const mln_point(I)& p);
+ const I& ima() const;
+ const mln_point(I)& p() const;
+ private:
+ const I& ima_;
+ const mln_point(I)& p_;
+ };
+
+
+ /// Routine to construct a pix on the fly.
+ template <typename I>
+ pix_<I>
+ pix(const Image<I>& ima, const mln_point(I)& p);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ // pix_<I>
+
+ template <typename I>
+ pix_<I>::pix_(const Image<I>& ima, const mln_point(I)& p)
+ : ima_(exact(ima)),
+ p_(p)
+ {
+ }
+
+ template <typename I>
+ const I&
+ pix_<I>::ima() const
+ {
+ return ima_;
+ }
+
+ template <typename I>
+ const mln_point(I)&
+ pix_<I>::p() const
+ {
+ return p_;
+ }
+
+ // pix
+
+ template <typename I>
+ pix_<I>
+ pix(const Image<I>& ima, const mln_point(I)& p)
+ {
+ pix_<I> tmp(ima, p);
+ return tmp;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace mln::util
+
+} // end of namespace mln
+
+
+#endif // ! MLN_UTIL_PIX_HH
URL: https://svn.lrde.epita.fr/svn/oln/trunk/milena
ChangeLog:
2007-09-07 Simon Nivault <simon.nivault(a)lrde.epita.fr>
Median can be processed for any direction
* sandbox/nivault/median.hh: .
* sandbox/nivault/tests/test.cc: Test on lena for median_dir
median.hh | 78 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++-
tests/test.cc | 51 +++++++++++++++++++++++++++++++++++++
2 files changed, 128 insertions(+), 1 deletion(-)
Index: trunk/milena/sandbox/nivault/tests/test.cc
===================================================================
--- trunk/milena/sandbox/nivault/tests/test.cc (revision 0)
+++ trunk/milena/sandbox/nivault/tests/test.cc (revision 1083)
@@ -0,0 +1,51 @@
+// Copyright (C) 2007 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.
+
+/*! \file tests/level_median.cc
+ *
+ * \brief Test on mln::median::median_dir.
+ */
+
+#include <median.hh>
+#include <mln/io/load_pgm.hh>
+#include <mln/io/save_pgm.hh>
+#include <mln/level/paste.hh>
+#include <mln/core/win/hline2d.hh>
+
+int main()
+{
+ using namespace mln;
+
+ image2d_b< value::int_u8 >
+ lena = io::load_pgm("lena.pgm"),
+ out = image2d_b< value::int_u8 >(lena.domain());
+
+ win::hline2d win(7);
+
+ level::impl::median_dir(lena, win, 0, out);
+ io::save_pgm(out, "out.pgm");
+}
Index: trunk/milena/sandbox/nivault/median.hh
===================================================================
--- trunk/milena/sandbox/nivault/median.hh (revision 1082)
+++ trunk/milena/sandbox/nivault/median.hh (revision 1083)
@@ -38,7 +38,9 @@
# include <mln/core/window2d.hh>
# include <mln/core/win/hline2d.hh>
+# include <mln/core/win/vline2d.hh>
# include <mln/core/t_image.hh>
+# include <mln/core/dpoint.hh>
# include <mln/accu/median.hh>
# include <mln/canvas/sbrowsing.hh>
@@ -46,6 +48,8 @@
# include <mln/geom/shift.hh>
# include <mln/set/diff.hh>
+# include <mln/border/resize.hh>
+# include <mln/border/duplicate.hh>
namespace mln
{
@@ -73,6 +77,76 @@
namespace impl
{
+ template <typename I, typename O>
+ void median_dir(const Image<I>& input_, const win::hline2d& win, unsigned dir, O& output)
+ {
+ const unsigned dim = I::point::dim;
+ mln_precondition(dir < dim);
+ const I& input = exact(input_);
+ mln_point(I)
+ pmin = input.domain().pmin(),
+ pmax = input.domain().pmax();
+
+ const unsigned half = win.length() / 2;
+
+ mln_point(I) p;
+ mln_point(I) pt;
+ mln_point(I) pu;
+
+ mln_coord(I)& ct = pt[dir];
+ mln_coord(I)& cu = pu[dir];
+
+ accu::median<mln_vset(I)> med(input.values());
+
+ p = pmin;
+ do
+ {
+ //traitement
+ pt = pu = p;
+
+ // initialization (before first point of the row)
+ med.init();
+ for (ct = pmin[dir]; ct < pmin[dir] + half; ++ct)
+ med.take(input(pt));
+
+ // left columns (just take new points)
+ for (p[dir] = pmin[dir]; p[dir] <= pmin[dir] + half; ++p[dir], ++ct)
+ {
+ med.take(input(pt));
+ output(p) = med.to_value();
+ }
+
+ // middle columns (both take and untake)
+ cu = pmin[dir];
+ for (; p[dir] <= pmax[dir] - half; ++cu, ++p[dir], ++ct)
+ {
+ med.take(input(pt));
+ med.untake(input(pu));
+ output(p) = med.to_value();
+ }
+
+ // right columns (now just untake old points)
+ for (; p[dir] <= pmax[dir]; ++cu, ++p[dir])
+ {
+ med.untake(input(pu));
+ output(p) = med.to_value();
+ }
+
+ // next line
+ for (int c = dim - 1; c >= 0; --c)
+ {
+ if (c == dir)
+ continue;
+ if (p[c] != pmax[c])
+ {
+ ++p[c];
+ break;
+ }
+ p[c] = pmin[c];
+ }
+ p[dir] = pmin[dir];
+ } while (p != pmin);
+ }
template <typename I, typename O>
void median(const Image<I>& input_, const win::hline2d& win, O& output)
@@ -183,7 +257,9 @@
}
template <typename I, typename O>
- void median(const I& input, const win::vline2d& win, O& output)
+ void median(const I& input,
+ const win::vline2d& win,
+ O& output)
{
t_image<O> swap_output = swap_coords(output, 0, 1);
impl::median(swap_coords(input, 0, 1),
URL: https://svn.lrde.epita.fr/svn/oln/trunk/milena
ChangeLog:
2007-09-06 Matthieu Garrigues <garrigues.matthieu(a)lrde.epita.fr>
add println_with_border
* mln/debug/println.hh:
add 3 function :
println_with_border(const box2d& b, const Fast_Image<I>& input_)
impl::println_with_border(const S&, const Fast_Image<I>& input_)
impl::println_with_border(const box2d& b, const Fast_Image<I>& input_)
* tests/println_with_border.cc: New.
mln/debug/println.hh | 30 +++++++++++++++++++++++++++
tests/println_with_border.cc | 47 +++++++++++++++++++++++++++++++++++++++++++
2 files changed, 77 insertions(+)
Index: trunk/milena/tests/println_with_border.cc
===================================================================
--- trunk/milena/tests/println_with_border.cc (revision 0)
+++ trunk/milena/tests/println_with_border.cc (revision 1082)
@@ -0,0 +1,47 @@
+// Copyright (C) 2007 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.
+
+/*! \file tests/println_with_border.cc
+ *
+ * \brief Test on mln::debug::println_with_border.
+ */
+
+#include <mln/core/image2d_b.hh>
+#include <mln/level/fill.hh>
+#include <mln/debug/println.hh>
+
+
+using namespace mln;
+
+
+int main()
+{
+ border::thickness = 3;
+ image2d_b<bool> msk(3, 3);
+ msk.at(1, 1) = true;
+ debug::println_with_border(msk);
+}
Index: trunk/milena/mln/debug/println.hh
===================================================================
--- trunk/milena/mln/debug/println.hh (revision 1081)
+++ trunk/milena/mln/debug/println.hh (revision 1082)
@@ -67,6 +67,16 @@
std::cout << std::endl;
}
+ template <typename S, typename I>
+ void println_with_border(const S&, const Fast_Image<I>& input_)
+ {
+ const I& input = exact(input_);
+ std::cout << input.ncells() << std::endl;
+ for (int i = 0; i < input.ncells(); i++)
+ std::cout << input.buffer()[i] << ' ';
+ std::cout << std::endl;
+ }
+
// 2D version
template <typename I>
void println(const box2d& b, const I& input)
@@ -88,6 +98,20 @@
std::cout << std::endl;
}
+ template <typename I>
+ void println_with_border(const box2d& b, const Fast_Image<I>& input_)
+ {
+ const I& input = exact(input_);
+ const int ncols = b.ncols() + 2 * input.border();
+ for (int i = 0; i < input.ncells(); i++)
+ {
+ std::cout << input.buffer()[i] << ' ';
+ if (((i+1) % ncols) == 0)
+ std::cout << std::endl;
+ }
+ std::cout << std::endl;
+ }
+
} // end of namespace mln::debug::impl
@@ -100,6 +124,12 @@
impl::println(exact(input).bbox(), exact(input));
}
+ template <typename I>
+ void println_with_border(const Fast_Image<I>& input)
+ {
+ impl::println_with_border(exact(input).bbox(), exact(input));
+ }
+
# endif // ! MLN_INCLUDE_ONLY
} // end of namespace mln::debug
https://svn.lrde.epita.fr/svn/oln/trunk/milena
Index: ChangeLog
from Thierry Geraud <thierry.geraud(a)lrde.epita.fr>
Add memcpy_ and memset_ for fast images; some fixes.
* tests/histo.cc: Augment.
* tests/level_memcpy_.cc: New.
* tests/level_memset_.cc: New.
* mln/convert/to_vec_p.hh: Typos.
* mln/core/concept/generalized_pixel.hh (doc): Fix.
* mln/core/concept/fast_image.hh (ncells): New.
Add FIXMEs.
* mln/core/concept/doc/fast_image.hh: Update.
* mln/level/fill.hh (fill_with_value): Use memset_.
* mln/level/memset_.hh: New.
* mln/level/memcpy_.hh: New.
* mln/value/int_s.hh (props): Fix card_.
(int_s): Fix preconditions.
mln/convert/to_vec_p.hh | 16 ++--
mln/core/concept/doc/fast_image.hh | 7 +
mln/core/concept/fast_image.hh | 16 ++--
mln/core/concept/generalized_pixel.hh | 4 -
mln/level/fill.hh | 17 ----
mln/level/memcpy_.hh | 112 ++++++++++++++++++++++++++++
mln/level/memset_.hh | 133 ++++++++++++++++++++++++++++++++++
mln/value/int_s.hh | 14 ++-
tests/histo.cc | 22 +++++
tests/level_memcpy_.cc | 58 ++++++++++++++
tests/level_memset_.cc | 53 +++++++++++++
11 files changed, 416 insertions(+), 36 deletions(-)
Index: tests/histo.cc
--- tests/histo.cc (revision 1080)
+++ tests/histo.cc (working copy)
@@ -34,8 +34,10 @@
#include <mln/core/image2d_b.hh>
#include <mln/value/int_u8.hh>
+#include <mln/value/int_s.hh>
#include <mln/debug/iota.hh>
+#include <mln/debug/println.hh>
#include <mln/accu/histo.hh>
#include <mln/histo/compute.hh>
@@ -62,8 +64,28 @@
{
image2d_b<int_u8> ima(3, 3);
debug::iota(ima);
+ ima.at(0,0) = 2;
+ debug::println(ima);
+
histo::data< value::set<int_u8> > h = histo::compute(ima);
std::cout << h << std::endl;
+
+ int_u8 i = 2;
+ std::cout << h(i) << std::endl;
}
+// {
+// typedef value::int_s<5> int_s5;
+// image2d_b<int_s5> ima(3, 3);
+// debug::iota(ima);
+// ima.at(0,0) = 2;
+// debug::println(ima);
+
+// histo::data< value::set<int_s5> > h = histo::compute(ima);
+// std::cout << h(2) << std::endl;
+
+// for (unsigned i = 0; i < h.vset().nvalues(); ++i)
+// std::cout << h[i] << std::endl;
+// }
+
}
Index: tests/level_memcpy_.cc
--- tests/level_memcpy_.cc (revision 0)
+++ tests/level_memcpy_.cc (revision 0)
@@ -0,0 +1,58 @@
+// Copyright (C) 2007 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.
+
+/*! \file tests/level_memcpy_.cc
+ *
+ * \brief Tests on mln::level::memcpy_.
+ *
+ * \todo Make this test not dummy!
+ */
+
+#include <mln/core/image2d_b.hh>
+#include <mln/core/inplace.hh>
+#include <mln/debug/iota.hh>
+#include <mln/level/memcpy_.hh>
+
+
+int main()
+{
+ using namespace mln;
+
+ typedef image2d_b<int> I;
+ I ima(3, 3);
+ debug::iota(ima);
+
+ point2d
+ src = make::point2d(0, 2),
+ dest = make::point2d(1, 2);
+
+ level::memcpy_(inplace(make::pixel(ima, dest)),
+ make::pixel(ima, src),
+ 2 + 2 * ima.border());
+
+ mln_assertion(ima(dest) = ima(src));
+}
Index: tests/level_memset_.cc
--- tests/level_memset_.cc (revision 0)
+++ tests/level_memset_.cc (revision 0)
@@ -0,0 +1,53 @@
+// Copyright (C) 2007 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.
+
+/*! \file tests/level_memset_.cc
+ *
+ * \brief Tests on mln::level::memset_.
+ */
+
+#include <mln/core/image2d_b.hh>
+#include <mln/geom/ncols.hh>
+#include <mln/level/fill.hh>
+#include <mln/level/memset_.hh>
+
+
+int main()
+{
+ using namespace mln;
+
+ image2d_b<int> ima(3, 3);
+ level::fill(ima, 0);
+ int X = 9;
+ level::memset_(ima, make::point2d(0,0),
+ X,
+ geom::ncols(ima) + 2 * ima.border() + 1);
+ // ^
+ // |
+ mln_assertion(ima.at(1,0) = X); // <----------------+
+ mln_assertion(ima.at(1,1) != X);
+}
Index: mln/convert/to_vec_p.hh
--- mln/convert/to_vec_p.hh (revision 1080)
+++ mln/convert/to_vec_p.hh (working copy)
@@ -34,6 +34,7 @@
*/
# include <mln/core/vec_p.hh>
+# include <mln/core/concept/window.hh>
namespace mln
@@ -47,9 +48,9 @@
vec_p<mln_point(S)> to_vec_p(const Point_Set<S>& pset);
- /// Convert a window \p win with a point \p p into a vec_p (point set vector).
+ /// Convert a window \p win centered at point \p p into a vec_p (point set vector).
template <typename W>
- vec_p<mln_point(W)> to_vec_p(const Window<W>& win, const mln_point(W) p);
+ vec_p<mln_point(W)> to_vec_p(const Window<W>& win, const mln_point(W)& p);
# ifndef MLN_INCLUDE_ONLY
@@ -67,17 +68,16 @@
}
template <typename W>
- vec_p<mln_point(W)> to_vec_p(const Window<W>& win, const mln_point(W) p_center)
+ vec_p<mln_point(W)> to_vec_p(const Window<W>& win, const mln_point(W)& p)
{
vec_p<mln_point(W)> v;
- mln_qiter(W) dp(win, p_center);
-
v.reserve(exact(win).ndpoints());
-
- for_all(dp)
- v.append(dp);
+ mln_qiter(W) q(win, p);
+ for_all(q)
+ v.append(q);
return v;
}
+
# endif // ! MLN_INCLUDE_ONLY
} // end of namespace mln::convert
Index: mln/core/concept/generalized_pixel.hh
--- mln/core/concept/generalized_pixel.hh (revision 1080)
+++ mln/core/concept/generalized_pixel.hh (working copy)
@@ -41,13 +41,9 @@
namespace mln
{
- // FIXME: \class Generalized_Pixel Generalized_Pixel.hh "mln/core/concept/doc/Generalized_Pixel.hh"
-
/*! \brief Base class for implementation classes that are pixels or that
* have the behavior of pixels.
*
- * "Generalized_Pixel" is "Generalized Pixel" for short.
- *
* \warning This class does \em not derive from mln::Object; it is
* for use as a parallel hierarchy.
*
Index: mln/core/concept/fast_image.hh
--- mln/core/concept/fast_image.hh (revision 1080)
+++ mln/core/concept/fast_image.hh (working copy)
@@ -51,7 +51,7 @@
/*
unsigned border();
- int offset(const dpoint& dp) const;
+ int offset(const dpoint& dp) const; // FIXME: std::ptr_diff_t?
point point_at_offset(unsigned o) const;
mln_qlf_value(E)* buffer();
@@ -59,6 +59,8 @@
rvalue operator[](unsigned o) const;
lvalue operator[](unsigned o);
+
+ std::size_t ncells() const;
*/
@@ -72,7 +74,8 @@
* \post p = point_at_offset(result)
*/
template <typename P>
- unsigned offset(const Generalized_Point<P>& p) const;
+ unsigned
+ offset_at(const Generalized_Point<P>& p) const;
protected:
Fast_Image();
@@ -83,11 +86,11 @@
template <typename E>
template <typename P>
- unsigned
- Fast_Image<E>::offset(const Generalized_Point<P>& p_) const
+ unsigned // FIXME: std::size_t?
+ Fast_Image<E>::offset_at(const Generalized_Point<P>& p_) const
{
// FIXME: check that P is mln_point(E)
- const E& this_ = exact(this);
+ const E* this_ = exact(this);
const P& p = internal::force_exact<P>(p_);
mln_precondition(this_->has_data());
mln_precondition(this_->owns_(p));
@@ -128,6 +131,9 @@
lvalue (E::*m7)(unsigned) = & E::operator[];
m7 = 0;
+ std::size_t (E::*m8)() const = & E::ncells;
+ m8 = 0;
+
// FIXME: how to check that qixter are defined when W is unknown!
}
Index: mln/core/concept/doc/fast_image.hh
--- mln/core/concept/doc/fast_image.hh (revision 1080)
+++ mln/core/concept/doc/fast_image.hh (working copy)
@@ -97,6 +97,13 @@
*/
lvalue operator[](unsigned o);
+
+ /*! \brief Give the number of pixels of the image including
+ * those of the virtual border.
+ *
+ * \pre The image has to be initialized.
+ */
+ std::size_t ncells() const;
};
} // end of namespace mln::doc
Index: mln/level/fill.hh
--- mln/level/fill.hh (revision 1080)
+++ mln/level/fill.hh (working copy)
@@ -39,6 +39,7 @@
# include <mln/core/concept/image.hh>
# include <mln/core/concept/function.hh>
+# include <mln/level/memset_.hh>
namespace mln
@@ -131,10 +132,8 @@
// fill_with_value
template <typename I>
- void fill_with_value(Image<I>& ima_, const mln_value(I)& value,
- bool force_call = false)
+ void fill_with_value(Image<I>& ima_, const mln_value(I)& value)
{
- force_call = false; // just to avoid warning ("unused param")
I& ima = exact(ima_);
mln_piter(I) p(ima.domain());
for_all(p)
@@ -145,17 +144,7 @@
void fill_with_value(Fast_Image<I>& ima_, const mln_value(I)& value)
{
I& ima = exact(ima_);
- if (sizeof(mln_value(I)) = 1)
- {
- std::memset((void*)(ima.buffer()),
- *(const int*)(& value), // violent cast
- sizeof(mln_value(I)) * ima.ncells());
- }
- else
- {
- // FIXME: Use memcpy on a chunck when image size is large!
- fill_with_value(ima, value, true);
- }
+ level::memset_(ima, ima.point_at_offset(0), value, ima.ncells());
}
Index: mln/level/memset_.hh
--- mln/level/memset_.hh (revision 0)
+++ mln/level/memset_.hh (revision 0)
@@ -0,0 +1,133 @@
+// Copyright (C) 2007 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_LEVEL_MEMSET_HH
+# define MLN_LEVEL_MEMSET_HH
+
+/*! \file mln/level/memset_.hh
+ *
+ * \brief Same as std::memset but for fast images.
+ */
+
+# include <mln/core/concept/fast_image.hh>
+# include <mln/core/pixel.hh>
+
+
+namespace mln
+{
+
+ namespace level
+ {
+
+ /*! Set \p n pixels at value \p v starting from pixel \p p.
+ *
+ * \param[in,out] pix The first pixel to set.
+ * \param[in] v The value to set pixels with.
+ * \param[in] n The number of pixels to set.
+ *
+ * \pre FIXME: !
+ */
+ template <typename P>
+ void memset_(Generalized_Pixel<P>& pix,
+ const mln_value(P)& v, std::size_t n);
+
+ /*! Set \p n points of image \p ima at value \p v starting from
+ * point \p p.
+ *
+ * \param[in,out] input The image.
+ * \param[in] p The first point to set.
+ * \param[in] v The value to set to points.
+ * \param[in] n The number of points to set.
+ *
+ * \pre \p input has to be initialized. FIXME: More.
+ */
+ template <typename I>
+ void memset_(Fast_Image<I>& input, const mln_point(I)& p,
+ const mln_value(I)& v, std::size_t n);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename P>
+ void memset_(Generalized_Pixel<P>& pix_,
+ const mln_value(P)& v, std::size_t n)
+ {
+ typedef mln_image(P) I;
+ // FIXME: metal::is_not_const<I>::check();
+
+ P& pix = internal::force_exact<P>(pix_);
+ mln_precondition(pix.ima().has_data());
+ mln_precondition(& pix.val() >= & pix.ima()[0]);
+ mln_precondition(& pix.val() < & pix.ima()[0] + pix.ima().ncells());
+ mln_precondition(& pix.val() + n <= & pix.ima()[0] + pix.ima().ncells());
+
+ if (n = 0)
+ {
+ return; // no-op
+ }
+
+ if (n = 1)
+ {
+ pix.val() = v; // one assignment
+ return;
+ }
+
+ if (sizeof(mln_value(I)) = 1)
+ {
+ std::memset((void*)(& pix.val()),
+ *(const int*)(&v), // violent cast
+ n);
+ }
+ else
+ {
+ mln_value(I)* ptr = & pix.val();
+ for (std::size_t i = 0; i < n; ++i)
+ *ptr++ = v;
+ }
+ }
+
+ template <typename I>
+ void memset_(Fast_Image<I>& input_, const mln_point(I)& p,
+ const mln_value(I)& v, std::size_t n)
+ {
+ I& input = exact(input_);
+ mln_precondition(input.has_data());
+ mln_precondition(input.owns_(p));
+ mln_precondition(input.offset_at(p) + n <= input.ncells());
+
+ pixel<I> pix(input, p);
+ memset_(pix, v, n);
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace mln::level
+
+} // end of namespace mln
+
+
+#endif // ! MLN_LEVEL_MEMSET_HH
Index: mln/level/memcpy_.hh
--- mln/level/memcpy_.hh (revision 0)
+++ mln/level/memcpy_.hh (revision 0)
@@ -0,0 +1,112 @@
+// Copyright (C) 2007 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_LEVEL_MEMCPY_HH
+# define MLN_LEVEL_MEMCPY_HH
+
+/*! \file mln/level/memcpy_.hh
+ *
+ * \brief Same as std::memcpy but for fast images.
+ *
+ * \todo Overload with images and points; Cf. memset_.
+ */
+
+# include <mln/core/concept/fast_image.hh>
+# include <mln/core/pixel.hh>
+
+
+namespace mln
+{
+
+ namespace level
+ {
+
+ /*! Copy \p n pixels starting from pixel \p src to destination
+ * starting from pixel \p dest.
+ *
+ * \param[in,out] dest The destination pixel (to set values).
+ * \param[in] v The source pixel (to get values).
+ * \param[in] n The number of pixels to copy.
+ *
+ * \pre FIXME: !
+ */
+ template <typename Pd, typename Ps>
+ void memcpy_(Generalized_Pixel<Pd>& dest, const Generalized_Pixel<Ps>& src,
+ std::size_t n);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ template <typename Pd, typename Ps>
+ void memcpy_(Generalized_Pixel<Pd>& dest_, const Generalized_Pixel<Ps>& src_,
+ std::size_t n)
+ {
+ typedef mln_image(Pd) Id;
+ // FIXME: metal::is_not_const<Id>::check();
+ typedef mln_image(Ps) Is;
+ Pd& dest = internal::force_exact<Pd>(dest_);
+ Ps& src = internal::force_exact<Ps>(src_);
+
+ mln_precondition(sizeof(mln_value(Id)) = sizeof(mln_value(Is)));
+ mln_precondition(dest.ima().has_data());
+ mln_precondition(src.ima().has_data());
+ // FIXME: Add precondition about n.
+
+ if (n = 0)
+ {
+ return; // no-op
+ }
+
+ if (n = 1)
+ {
+ dest.val() = src.val(); // one assignment
+ return;
+ }
+
+ if (sizeof(mln_value(Id)) = 1)
+ {
+ std::memcpy(( void*)(& dest.val()), // violent casts
+ (const void*)(& src.val()),
+ n);
+ }
+ else
+ {
+ mln_value(Id)* p_d = & dest.val();
+ const mln_value(Is)* p_s = & src.val();
+ for (std::size_t i = 0; i < n; ++i)
+ *p_d++ = *p_s++;
+ }
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace mln::level
+
+} // end of namespace mln
+
+
+#endif // ! MLN_LEVEL_MEMCPY_HH
Index: mln/value/int_s.hh
--- mln/value/int_s.hh (revision 1080)
+++ mln/value/int_s.hh (working copy)
@@ -101,7 +101,7 @@
template <unsigned n>
struct props< int_s<n> >
{
- static const std::size_t card_ = metal::pow<2, n>::value;
+ static const std::size_t card_ = metal::pow<2, n>::value - 1;
static const int_s<n> max() { return metal::pow<2, n-1>::value - 1; }
static const int_s<n> min() { return - max(); }
static const unsigned nbits = n;
@@ -132,8 +132,10 @@
template <unsigned n>
int_s<n>::int_s(int i)
{
- mln_precondition(i >= mln_min(enc));
- mln_precondition(i <= mln_max(enc));
+ static const int max = metal::pow<2, n-1>::value - 1;
+ static const int min = - max;
+ mln_precondition(i >= min);
+ mln_precondition(i <= max);
this->v_ = enc(i);
}
@@ -141,8 +143,10 @@
int_s<n>&
int_s<n>::operator=(int i)
{
- mln_precondition(i >= mln_min(enc));
- mln_precondition(i <= mln_max(enc));
+ static const int max = metal::pow<2, n-1>::value - 1;
+ static const int min = - max;
+ mln_precondition(i >= min);
+ mln_precondition(i <= max);
this->v_ = i;
return *this;
}
URL: https://svn.lrde.epita.fr/svn/oln/trunk/milena
ChangeLog:
2007-09-06 Matthieu Garrigues <garrigues.matthieu(a)lrde.epita.fr>
add convertion from histo to image1d
* mln/convert/to_image.hh: add the function
* tests/histo_to_image1d_b.cc: a test
mln/convert/to_image.hh | 14 ++++++++
tests/histo_to_image1d_b.cc | 77 ++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 91 insertions(+)
Index: trunk/milena/tests/histo_to_image1d_b.cc
===================================================================
--- trunk/milena/tests/histo_to_image1d_b.cc (revision 0)
+++ trunk/milena/tests/histo_to_image1d_b.cc (revision 1080)
@@ -0,0 +1,77 @@
+// Copyright (C) 2007 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.
+
+/*! \file tests/histo.cc
+ *
+ * \brief Tests on mln::accu::histo<S> and mln::histo::data<S>.
+ */
+
+#include <iterator>
+
+#include <mln/core/image2d_b.hh>
+#include <mln/core/image1d_b.hh>
+
+#include <mln/value/int_u8.hh>
+
+#include <mln/debug/iota.hh>
+#include <mln/accu/histo.hh>
+#include <mln/histo/compute.hh>
+
+#include <mln/debug/println.hh>
+
+#include <mln/convert/to_image.hh>
+
+int main()
+{
+ using namespace mln;
+ using value::int_u8;
+
+ {
+ accu::histo< value::set<bool> > h;
+
+ for (unsigned i = 0; i < 5; ++i)
+ h.take(false);
+ for (unsigned i = 0; i < 2; ++i)
+ h.take(true);
+ h.untake(true);
+
+ mln_assertion(h[0] * 10 + h[1] == 51);
+ mln_assertion(h(false) * 10 + h(true) == 51);
+ }
+
+ {
+ image2d_b<int_u8> ima(3, 3);
+ debug::iota(ima);
+ ima(make::point2d(0,1)) = 255;
+ debug::println(ima);
+ histo::data< value::set<int_u8> > h = histo::compute(ima);
+ std::cout << h << std::endl;
+
+ image1d_b<std::size_t> ima2 = convert::to_image(h);
+ debug::println(ima2);
+ }
+}
Index: trunk/milena/mln/convert/to_image.hh
===================================================================
--- trunk/milena/mln/convert/to_image.hh (revision 1079)
+++ trunk/milena/mln/convert/to_image.hh (revision 1080)
@@ -111,6 +111,9 @@
template <typename W>
mln_image_from(W, mln_weight(W)) to_image(const Weighted_Window<W>& w_win);
+ /// Convert an histo \p h into an image1d_b.
+ template <typename S>
+ image1d_b<std::size_t> to_image(const histo::data<S>& h);
# ifndef MLN_INCLUDE_ONLY
@@ -163,6 +166,17 @@
return ima;
}
+ template <typename S>
+ image1d_b<std::size_t> to_image(const histo::data<S>& h)
+ {
+ mln_value(S)
+ v_min = h.vset()[0],
+ v_max = h.vset()[h.vset().nvalues() - 1];
+ image1d_b<std::size_t> ima(make::box1d(v_min, v_max));
+ for(std::size_t i = 0; i < h.vset().nvalues(); ++i)
+ ima[i] = h[i];
+ return ima;
+ }
# endif // ! MLN_INCLUDE_ONLY