https://svn.lrde.epita.fr/svn/oln/trunk/milena/sandbox
Index: ChangeLog
from Alexandre Abraham <abraham(a)lrde.epita.fr>
Add Autarkical Leveling, move files ot trunk.
* abraham/tests/morpho/levelings.cc: New
Test for autorkical leveling.
* abraham/tests/morpho/red_erosion.cc: New
Make red erosion with fun_image (not working yet).
* abraham/tests/morpho/red_erosion3.cc: New
Make red erosion with mixin.
* abraham/tests/fun/meta/red.cc: Update.
* abraham/tests/core/image/fun_image_const.cc: New.
* abraham/tests/core/image/fun_image_norm.cc: New.
* abraham/tests/core/image/fun_image_v2v.cc: New.
* abraham/tests/core/image/fun_image_v2w2v.cc: New.
* abraham/tests/value/mixin.cc: Update.
* abraham/mln/morpho/autarkical_leveling.hh: New
Autarkical leveling (see Golima).
* abraham/mln/morpho/topo_wst.hh: Update.
* abraham/mln/morpho/vector_median.hh: New
Morphological operator needed for autarkical leveliing.
* abraham/mln/core/image/thru.hh: Move to trunk under the
name fun_image.hh.
* abraham/mln/core/image/violent_cast_image.hh: Move to trunk.
* abraham/mln/core/concept/function.hh: Move to trunk.
* abraham/mln/fun/v2w2v: Move to trunk.
* abraham/mln/fun/v2w2v/cos.hh: Move to trunk.
* abraham/mln/fun/meta: Move to trunk.
* abraham/mln/fun/meta/hue.hh: Move to trunk.
* abraham/mln/fun/meta/inty.hh: Move to trunk.
* abraham/mln/fun/meta/sat.hh: Move to trunk.
* abraham/mln/fun/meta/to_enc.hh: Move to trunk.
* abraham/mln/fun/meta/red.hh: Move to trunk.
* abraham/mln/fun/v2w_w2v: Move to trunk.
* abraham/mln/fun/v2w_w2v/norm.hh: Move to trunk.
* abraham/mln/value/mixin.hh: Move to trunk.
* abraham/mln/value/op_less.hh: Move to trunk.
mln/core/concept/function.hh | 526 -----------------------------------
mln/core/image/thru.hh | 193 ------------
mln/core/image/violent_cast_image.hh | 180 -----------
mln/fun/meta/hue.hh | 64 ----
mln/fun/meta/inty.hh | 65 ----
mln/fun/meta/red.hh | 44 --
mln/fun/meta/sat.hh | 64 ----
mln/fun/meta/to_enc.hh | 57 ---
mln/fun/v2w2v/cos.hh | 95 ------
mln/fun/v2w_w2v/norm.hh | 155 ----------
mln/morpho/autarkical_leveling.hh | 290 +++++++++++++++++++
mln/morpho/topo_wst.hh | 24 -
mln/morpho/vector_median.hh | 129 ++++++++
mln/value/mixin.hh | 156 ----------
mln/value/op_less.hh | 46 ---
tests/core/image/fun_image_const.cc | 64 ++++
tests/core/image/fun_image_norm.cc | 63 ++++
tests/core/image/fun_image_v2v.cc | 56 +++
tests/core/image/fun_image_v2w2v.cc | 64 ++++
tests/fun/meta/red.cc | 4
tests/morpho/levelings.cc | 66 ++++
tests/morpho/red_erosion.cc | 41 ++
tests/morpho/red_erosion3.cc | 65 ++++
tests/value/mixin.cc | 14
24 files changed, 860 insertions(+), 1665 deletions(-)
Index: abraham/tests/morpho/levelings.cc
--- abraham/tests/morpho/levelings.cc (revision 0)
+++ abraham/tests/morpho/levelings.cc (revision 0)
@@ -0,0 +1,66 @@
+#include <mln/core/image/image2d.hh>
+#include <mln/io/ppm/save.hh>
+#include <mln/io/ppm/load.hh>
+#include <mln/value/int_u8.hh>
+#include <mln/morpho/vector_median.hh>
+#include <mln/morpho/autarkical_leveling.hh>
+#include <mln/fun/meta/red.hh>
+#include <mln/value/rgb8.hh>
+#include <mln/value/mixin.hh>
+#include <mln/core/image/fun_image.hh>
+#include <mln/core/image/violent_cast_image.hh>
+
+namespace mln
+{
+ struct red_only
+ {
+ template <unsigned n>
+ value::rgb<n> max_() const
+ {
+ return value::rgb<n>(mln_max(typename value::rgb<n>::red_t), 0, 0);
+ }
+
+ value::rgb8 max () const
+ {
+ return value::rgb8(255, 0, 0);
+ }
+
+ template <unsigned n>
+ bool less(const value::rgb<n>& a, const value::rgb<n>& b)
+ {
+ return a.red() < b.red();
+ }
+ };
+
+}
+
+
+int main (int argc, const char * argv[])
+{
+ using namespace mln;
+ using namespace value;
+
+ if (argc < 2) {
+ std::cerr << "usage: " << argv[0] << " in.pgm [other_files.pgm]" << std::endl;
+ return 1;
+ }
+
+ typedef value::mixin<value::rgb8,red_only> Rgb;
+
+ for (int i = 1; i < argc; ++i)
+ {
+ border::thickness = 2;
+
+ image2d<rgb8> ima;
+ io::ppm::load(ima, argv[i]);
+
+ std::string name(argv[i]);
+ name.erase(name.length() - 4);
+
+ win::rectangle2d rect(8, 8);
+
+ io::ppm::save(morpho::autarkical_leveling(ima, morpho::vector_median(ima, rect), rect), name.append("_autarkical_leveled.ppm"));
+
+ }
+ return 0;
+}
Index: abraham/tests/morpho/red_erosion.cc
--- abraham/tests/morpho/red_erosion.cc (revision 0)
+++ abraham/tests/morpho/red_erosion.cc (revision 0)
@@ -0,0 +1,41 @@
+#include <mln/core/image/image2d.hh>
+#include <mln/io/ppm/save.hh>
+#include <mln/io/ppm/load.hh>
+#include <mln/value/int_u8.hh>
+#include <mln/morpho/erosion.hh>
+#include <mln/fun/meta/red.hh>
+#include <mln/value/rgb8.hh>
+#include <mln/core/image/fun_image.hh>
+
+int main (int argc, const char * argv[])
+{
+ using namespace mln;
+ using namespace value;
+
+ typedef image2d<int_u8> image2dint;
+
+ if (argc < 2) {
+ std::cerr << "usage: " << argv[0] << " in.pgm [other_files.pgm]" << std::endl;
+ return 1;
+ }
+
+ for (int i = 1; i < argc; ++i)
+ {
+ border::thickness = 2;
+
+ image2d<rgb8> ima;
+ io::ppm::load(ima, argv[i]);
+
+ mln::fun_image<meta::red <rgb8>, image2d<rgb8> > red(ima);
+
+ std::string name(argv[i]);
+ name.erase(name.length() - 4);
+
+ win::rectangle2d rect(5, 5);
+ morpho::erosion(red, rect);
+
+ io::ppm::save(ima, name.append("_red_eroded.pgm"));
+
+ }
+ return 0;
+}
Index: abraham/tests/morpho/red_erosion3.cc
--- abraham/tests/morpho/red_erosion3.cc (revision 0)
+++ abraham/tests/morpho/red_erosion3.cc (revision 0)
@@ -0,0 +1,65 @@
+#include <mln/core/image/image2d.hh>
+#include <mln/io/ppm/save.hh>
+#include <mln/io/ppm/load.hh>
+#include <mln/value/int_u8.hh>
+#include <mln/morpho/erosion.hh>
+#include <mln/fun/meta/red.hh>
+#include <mln/value/rgb8.hh>
+#include <mln/value/mixin.hh>
+#include <mln/core/image/fun_image.hh>
+#include <mln/core/image/violent_cast_image.hh>
+
+namespace mln
+{
+ struct red_only
+ {
+ template <unsigned n>
+ value::rgb<n> max_() const
+ {
+ return value::rgb<n>(mln_max(typename value::rgb<n>::red_t), 0, 0);
+ }
+
+ value::rgb8 max () const
+ {
+ return value::rgb8(255, 0, 0);
+ }
+
+ template <unsigned n>
+ bool less(const value::rgb<n>& a, const value::rgb<n>& b)
+ {
+ return a.red() < b.red();
+ }
+ };
+
+}
+
+
+int main (int argc, const char * argv[])
+{
+ using namespace mln;
+ using namespace value;
+
+ if (argc < 2) {
+ std::cerr << "usage: " << argv[0] << " in.pgm [other_files.pgm]" << std::endl;
+ return 1;
+ }
+
+ typedef value::mixin<value::rgb8,red_only> Rgb;
+
+ for (int i = 1; i < argc; ++i)
+ {
+ border::thickness = 2;
+
+ image2d<rgb8> ima;
+ io::ppm::load(ima, argv[i]);
+
+ std::string name(argv[i]);
+ name.erase(name.length() - 4);
+
+ win::rectangle2d rect(5, 5);
+
+ io::ppm::save(violent_cast_image_<rgb8>(morpho::erosion(violent_cast_image_<Rgb>(ima), rect)), name.append("_red_eroded.pgm"));
+
+ }
+ return 0;
+}
Index: abraham/tests/fun/meta/red.cc
--- abraham/tests/fun/meta/red.cc (revision 3049)
+++ abraham/tests/fun/meta/red.cc (working copy)
@@ -1,6 +1,6 @@
#include <mln/fun/meta/red.hh>
#include <mln/core/image/image2d.hh>
-#include <mln/core/image/thru.hh>
+#include <mln/core/image/fun_image.hh>
namespace mln
{
@@ -52,7 +52,7 @@
c.r = 1;
i(mln::point2d(2,1)) = c;
- mln::thru<mln::meta::red <C>, mln::image2d<C> > out(i);
+ mln::fun_image<mln::meta::red <C>, mln::image2d<C> > out(i);
mln_piter_(mln::image2d<C>) p(i.domain());
Index: abraham/tests/core/image/fun_image_const.cc
--- abraham/tests/core/image/fun_image_const.cc (revision 0)
+++ abraham/tests/core/image/fun_image_const.cc (revision 0)
@@ -0,0 +1,64 @@
+// 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.
+
+# include <mln/core/image/image2d.hh>
+# include <mln/core/image/fun_image.hh>
+# include <mln/fun/v2w2v/cos.hh>
+
+int main ()
+{
+
+ using namespace mln;
+
+ typedef const image2d<double> I;
+
+ double vs[6][5] = {
+
+ { 12, -3, 8, -4, 6 },
+ { -2, 22, -1, 45, -1 },
+ { -1, -4, -4, -4, -1 },
+ { -1, -4, -3, -4, -1 },
+ { -1, -4, -5, -3, -1 },
+ { -1, -1, -1, -1, -1 }
+
+ };
+
+ I ima(make::image(vs));
+ fun_image<mln::fun::v2w2v::cos<double>, I > out(ima);
+
+ double i = 0;
+
+ box_fwd_piter_<point2d> p(ima.domain());
+ for_all (p)
+ {
+ out(p) = i;
+ i += 1./40.;
+ }
+
+ for_all (p)
+ std::cout << out(p) << std::endl;
+}
Index: abraham/tests/core/image/fun_image_norm.cc
--- abraham/tests/core/image/fun_image_norm.cc (revision 0)
+++ abraham/tests/core/image/fun_image_norm.cc (revision 0)
@@ -0,0 +1,63 @@
+// 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.
+
+# include <mln/core/image/image2d.hh>
+# include <mln/core/image/fun_image.hh>
+# include <mln/fun/v2w_w2v/norm.hh>
+# include <mln/algebra/vec.hh>
+# include <mln/level/fill.hh>
+# include <mln/core/image/violent_cast_image.hh>
+
+#include <mln/morpho/erosion.hh>
+
+int main ()
+{
+
+ using namespace mln;
+ typedef image2d<algebra::vec<2, double> > I;
+
+ I ima(3, 2, 0);
+
+ ima(point2d(0,0)).set (1, 1);
+ ima(point2d(0,1)).set (1, 3);
+ ima(point2d(1,0)).set (4, 4);
+ ima(point2d(1,1)).set (-1, 3);
+ ima(point2d(2,0)).set (23, 23);
+ ima(point2d(2,1)).set (3, 1);
+
+ fun_image<mln::fun::v2w_w2v::l1_norm<algebra::vec<2, double>, double>, I > out(ima);
+ // level::fill(out, 1);
+
+ win::rectangle2d rect(3, 3);
+ morpho::erosion(out, rect);
+
+
+ box_fwd_piter_<point2d> p(ima.domain());
+
+ for_all (p)
+ std::cout << ima(p) << std::endl;
+}
Index: abraham/tests/core/image/fun_image_v2v.cc
--- abraham/tests/core/image/fun_image_v2v.cc (revision 0)
+++ abraham/tests/core/image/fun_image_v2v.cc (revision 0)
@@ -0,0 +1,56 @@
+// 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.
+
+# include <mln/core/image/image2d.hh>
+# include <mln/core/image/fun_image.hh>
+# include <mln/fun/v2v/abs.hh>
+
+int main ()
+{
+
+ using namespace mln;
+
+ typedef image2d<int> I;
+
+ int vs[6][5] = {
+
+ { -3, -3, -4, -4, -4 },
+ { -2, -1, -1, -1, -1 },
+ { -1, -4, -4, -4, -1 },
+ { -1, -4, -3, -4, -1 },
+ { -1, -4, -5, -3, -1 },
+ { -1, -1, -1, -1, -1 }
+
+ };
+
+ image2d<int> ima(make::image(vs));
+ fun_image<mln::fun::v2v::abs<int>, image2d<int> > out(ima);
+
+ box_fwd_piter_<point2d> p(ima.domain());
+ for_all (p)
+ mln_assertion (out(p) >= 0);
+}
Index: abraham/tests/core/image/fun_image_v2w2v.cc
--- abraham/tests/core/image/fun_image_v2w2v.cc (revision 0)
+++ abraham/tests/core/image/fun_image_v2w2v.cc (revision 0)
@@ -0,0 +1,64 @@
+// 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.
+
+# include <mln/core/image/image2d.hh>
+# include <mln/core/image/fun_image.hh>
+# include <mln/fun/v2w2v/cos.hh>
+
+int main ()
+{
+
+ using namespace mln;
+
+ typedef image2d<double> I;
+
+ double vs[6][5] = {
+
+ { 12, -3, 8, -4, 6 },
+ { -2, 22, -1, 45, -1 },
+ { -1, -4, -4, -4, -1 },
+ { -1, -4, -3, -4, -1 },
+ { -1, -4, -5, -3, -1 },
+ { -1, -1, -1, -1, -1 }
+
+ };
+
+ image2d<double> ima(make::image(vs));
+ fun_image<mln::fun::v2w2v::cos<double>, image2d<double> > out(ima);
+
+ double i = 0;
+
+ box_fwd_piter_<point2d> p(ima.domain());
+ for_all (p)
+ {
+ out(p) = i;
+ i += 1./40.;
+ }
+
+ for_all (p)
+ std::cout << out(p) << std::endl;
+}
Index: abraham/tests/value/mixin.cc
--- abraham/tests/value/mixin.cc (revision 3049)
+++ abraham/tests/value/mixin.cc (working copy)
@@ -83,14 +83,16 @@
value::rgb8 r(12, 13, 14);
value::rgb8 s(13, 14, 15);
+ value::rgb8 t(13, 20, 17);
- typedef value::mixin<value::rgb8,red_only> Rgb;
+ std::cout << mln_max(value::rgb8::red_t) << std::endl;
- std::cout << ( my_violent_cast<Rgb>(r) < my_violent_cast<Rgb>(s) ) << std::endl;
+ typedef value::mixin<value::rgb8,red_only> Rgb;
+ assert(my_violent_cast<Rgb>(r) < my_violent_cast<Rgb>(s));
+ assert(my_violent_cast<Rgb>(s) > my_violent_cast<Rgb>(r));
+ assert(my_violent_cast<Rgb>(s) == my_violent_cast<Rgb>(t));
+ assert(my_violent_cast<Rgb>(s) >= my_violent_cast<Rgb>(t));
-// std::cout
-// << ( *(value::mixin<value::rgb8, value::op_less>*)(void*) &r <
-// *(value::mixin<value::rgb8, value::op_less>*)(void*) &s )
-// << std::endl;
+ return 0;
}
Index: abraham/mln/morpho/autarkical_leveling.hh
--- abraham/mln/morpho/autarkical_leveling.hh (revision 0)
+++ abraham/mln/morpho/autarkical_leveling.hh (revision 0)
@@ -0,0 +1,145 @@
+// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// 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_AUTARKICAL_LEVELING_HH
+# define MLN_MORPHO_AUTARKICAL_LEVELING_HH
+
+/// \file mln/morpho/autarkical_leveling.hh
+///
+/// Morphological autarkical leveling filter.
+///
+/// \todo The overloads are hidden and I don't know why!
+
+# include <mln/morpho/includes.hh>
+# include <mln/morpho/general.hh>
+# include <mln/accu/land.hh>
+# include <mln/accu/land_basic.hh>
+# include <mln/accu/min.hh>
+# include <mln/accu/min_h.hh>
+# include <mln/norm/l2.hh>
+
+namespace mln
+{
+
+ namespace morpho
+ {
+
+ /// Morphological autarkical_leveling.
+ template <typename I, typename W>
+ mln_concrete(I)
+ autarkical_leveling(const Image<I>& input, const Image<I>& marker, const Window<W>& win);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ namespace impl
+ {
+
+ // On set with centered window (overloads).
+
+ template <typename I, typename W>
+ mln_concrete(I)
+ autarkical_leveling(const Image<I>& input_, const Image<I>& marker_, const Window<W>& win_)
+ {
+ trace::entering("morpho::impl::general_on_set_centered__autarkical_leveling");
+
+ typedef mln_concrete(I) O;
+ const I& input = exact(input_);
+ const I& marker = exact(marker_);
+ const W& win = exact(win_);
+
+ O output;
+ output = clone(input);
+
+ bool modification = true;
+
+ mln_piter(I) p(input.domain());
+ mln_qiter(W) q(win, p);
+ mln_qiter(W) r(win, p);
+ for_all(p)
+ {
+ mln_psite(W) v;
+ double min_dist = std::numeric_limits<double>::infinity();
+ bool same_side = true;
+
+ for_all(q) if (input.domain().has(q))
+ {
+ for_all(r) if (input.domain().has(r) && q!=r)
+ if ((marker(q) - input(p)) * (marker(r) - input(p)) < 0)
+ {
+ same_side = false;
+ break;
+ }
+
+ if (!same_side)
+ break;
+
+ double dist = norm::l2(input(p) - marker(q));
+ if (dist < min_dist)
+ {
+ min_dist = dist;
+ v = q;
+ }
+ }
+ if (same_side)
+ output(p) = marker(v);
+ else
+ output(p) = input(p);
+ }
+
+ trace::exiting("morpho::impl::general_on_set_centered__autarkical_leveling");
+ return output;
+ }
+
+
+ } // end of namespace morpho::impl
+
+
+ template <typename I, typename W>
+ inline
+ mln_concrete(I)
+ autarkical_leveling(const Image<I>& input, const Image<I>& marker, const Window<W>& win)
+ {
+ trace::entering("morpho::autarkical_leveling");
+ mln_precondition(exact(input).has_data());
+ mln_precondition(! exact(win).is_empty());
+
+ mln_concrete(I) output = impl::autarkical_leveling(input, marker, win);
+
+ trace::exiting("morpho::autarkical_leveling");
+ return output;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace mln::morpho
+
+} // end of namespace mln
+
+
+#endif // ! MLN_MORPHO_AUTARKICAL_LEVELING_HH
Index: abraham/mln/morpho/topo_wst.hh
Index: abraham/mln/morpho/vector_median.hh
--- abraham/mln/morpho/vector_median.hh (revision 0)
+++ abraham/mln/morpho/vector_median.hh (revision 0)
@@ -0,0 +1,129 @@
+// Copyright (C) 2007, 2008 EPITA Research and Development Laboratory
+// (LRDE)
+//
+// This file is part of the Olena Library. This library is free
+// software; you can redistribute it and/or modify it under the terms
+// 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_VECTOR_MEDIAN_HH
+# define MLN_MORPHO_VECTOR_MEDIAN_HH
+
+/// \file mln/morpho/vector_median.hh
+///
+/// Morphological vector median filter.
+///
+/// \todo The overloads are hidden and I don't know why!
+
+# include <mln/morpho/includes.hh>
+# include <mln/morpho/general.hh>
+# include <mln/accu/land.hh>
+# include <mln/accu/land_basic.hh>
+# include <mln/accu/min.hh>
+# include <mln/accu/min_h.hh>
+# include <mln/norm/l2.hh>
+
+namespace mln
+{
+
+ namespace morpho
+ {
+
+ /// Morphological vector_median.
+ template <typename I, typename W>
+ mln_concrete(I)
+ vector_median(const Image<I>& input, const Window<W>& win);
+
+
+# ifndef MLN_INCLUDE_ONLY
+
+ namespace impl
+ {
+
+ // On set with centered window (overloads).
+
+ template <typename I, typename W>
+ mln_concrete(I)
+ vector_median(const Image<I>& input_, const Window<W>& win_)
+ {
+ trace::entering("morpho::impl::general_on_set_centered__vector_median");
+
+ typedef mln_concrete(I) O;
+ const I& input = exact(input_);
+ const W& win = exact(win_);
+
+ O output;
+ output = clone(input);
+
+ mln_piter(I) p(input.domain());
+ mln_qiter(W) q(win, p);
+ mln_qiter(W) r(win, p);
+ for_all(p)
+ {
+ mln_psite(W) v;
+ double min_dist = std::numeric_limits<double>::infinity();
+ for_all(q) if (input.domain().has(q))
+ {
+ double dist = 0;
+ for_all(r) if (input.domain().has(r) && q!=r)
+ dist += norm::l2(input(r) - input(q));
+ if (dist < min_dist)
+ {
+ min_dist = dist;
+ v = q;
+ }
+ }
+ output(p) = input(v);
+ }
+
+ trace::exiting("morpho::impl::general_on_set_centered__vector_median");
+ return output;
+ }
+
+
+ } // end of namespace morpho::impl
+
+
+ template <typename I, typename W>
+ inline
+ mln_concrete(I)
+ vector_median(const Image<I>& input, const Window<W>& win)
+ {
+ trace::entering("morpho::vector_median");
+ mln_precondition(exact(input).has_data());
+ mln_precondition(! exact(win).is_empty());
+
+ mln_concrete(I) output = impl::vector_median(input, win);
+
+ trace::exiting("morpho::vector_median");
+ return output;
+ }
+
+# endif // ! MLN_INCLUDE_ONLY
+
+ } // end of namespace mln::morpho
+
+} // end of namespace mln
+
+
+#endif // ! MLN_MORPHO_VECTOR_MEDIAN_HH
https://svn.lrde.epita.fr/svn/oln/trunk/milena/sandbox
Index: ChangeLog
from Thierry Geraud <thierry.geraud(a)lrde.epita.fr>
Fetch Ugo's code to prepare merging it with 1st steps.
* jardonnet/n_cmpt/n_cmpt5.hh: Fix typo.
Copy to...
* geraud/tufa_2008/n_cmpt.cc: ...this new file.
Cleanup code.
Fix typos.
(main): New.
geraud/tufa_2008/n_cmpt.cc | 190 ++++++++++++++++++++++++--------------------
jardonnet/n_cmpt/n_cmpt5.hh | 2
2 files changed, 105 insertions(+), 87 deletions(-)
Index: jardonnet/n_cmpt/n_cmpt5.hh
--- jardonnet/n_cmpt/n_cmpt5.hh (revision 3044)
+++ jardonnet/n_cmpt/n_cmpt5.hh (working copy)
@@ -96,7 +96,7 @@
// number of minima
unsigned cmpts = label;
if (lambda > cmpts)
- std::cout << "warning : lambda value is to hight." << std::endl;
+ std::cout << "Warning: lambda value is too high!" << std::endl;
std::cout << cmpts << std::endl;
Index: geraud/tufa_2008/n_cmpt.cc
--- geraud/tufa_2008/n_cmpt.cc (revision 3043)
+++ geraud/tufa_2008/n_cmpt.cc (working copy)
@@ -1,4 +1,4 @@
-// Copyright (C) 2008 EPITA Research and Development Laboratory
+// Copyright (C) 2008 EPITA Research and Development Laboratory (LRDE)
//
// This file is part of the Olena Library. This library is free
// software; you can redistribute it and/or modify it under the terms
@@ -25,78 +25,68 @@
// reasons why the executable file might be covered by the GNU General
// Public License.
-#ifndef MLN_N_CMPT3_HH
-# define MLN_N_CMPT3_HH
-
-# include <mln/labeling/regional_minima.hh>
+#include <mln/core/image/image2d.hh>
# include <mln/core/alias/neighb2d.hh>
-# include <mln/util/set.hh>
+
+#include <mln/value/int_u8.hh>
+#include <mln/value/int_u16.hh>
+#include <mln/io/pgm/load.hh>
# include <mln/debug/println.hh>
# include <mln/debug/iota.hh>
-# include <mln/accu/volume.hh>
+#include <mln/labeling/regional_minima.hh>
+#include <mln/level/fill.hh>
+
# include <mln/morpho/tree/data.hh>
# include <mln/morpho/tree/compute_attribute_image.hh>
-namespace mln
-{
-
- namespace n_cmpt
- {
+#include <mln/accu/volume.hh>
+#include <mln/accu/count.hh>
- template < typename I >
- void n_cmpt5(const I& (((((((ima))))))));
-# ifndef MLN_INCLUDE_ONLY
+namespace mln
+{
template <typename I>
inline
- mln_psite(I)
- find_root(I& parent,
- const mln_psite(I)& x)
+ mln_psite(I) find_root__(I& parent, const mln_psite(I)& x)
{
if (parent(x) == x)
return x;
else
- return parent(x) = find_root(parent, parent(x));
+ return parent(x) = find_root__(parent, parent(x));
}
- template < typename I, typename N>
- I
- n_cmpt3(const I& ima, const N& nbh,
- unsigned lambda)
- {
- std::cout << "/ima/" << std::endl;
- debug::println(ima);
- // compute volume image
- //---------------------
+ template <typename A, typename I, typename N>
+ mln_concrete(I)
+ n_cmpt(A a, const I& f, const N& nbh, unsigned lambda)
+ {
+ // Compute attribute image.
+ //-------------------------
typedef p_array<mln_psite(I)> S;
- typedef mln_ch_value(I,unsigned) V;
- typedef accu::volume<I> A;
+ typedef mln_ch_value(I, mln_result(A)) Attr;
- S sp = level::sort_psites_decreasing(ima);
- morpho::tree::data<I,S> t(ima, sp, nbh);
- V volume = morpho::tree::compute_attribute_image(A(), t);
- sp = level::sort_psites_increasing(volume);
- std::cout << "/volume/" << std::endl;
- debug::println(volume);
+ S s = level::sort_psites_decreasing(f);
+ morpho::tree::data<I,S> t(f, s, nbh);
+ Attr attr = morpho::tree::compute_attribute_image(a, t);
+ s = level::sort_psites_increasing(attr);
+ debug::println("attr =", attr);
- // get /volume/ regional minima
- //-----------------------------
+ // Compute regional minima of attribute image.
+ //--------------------------------------------
unsigned label;
- mln_ch_value(I, unsigned) min_v = labeling::regional_minima(volume, nbh, label);
- std::cout << "/volume/ regional minima" << std::endl;
- debug::println(min_v);
+ mln_ch_value(I, unsigned) min_v = labeling::regional_minima(attr, nbh, label);
+ debug::println("regmin =", min_v);
// number of minima
unsigned cmpts = label;
if (lambda > cmpts)
- std::cout << "warning : lambda value is to hight." << std::endl;
+ std::cout << "Warning: lambda value is too high!" << std::endl;
std::cout << cmpts << std::endl;
@@ -106,23 +96,21 @@
// init fused image
mln_ch_value(I, bool) fused;
- initialize(fused, volume);
+ initialize(fused, attr);
mln::level::fill(fused, false);
// prepare union find
- typedef mln_psite(V) P;
-
- //data
- mln_ch_value(V, accu::volume<V>) data(volume.domain());
+ typedef mln_psite(I) P;
//deja_vu
- mln_ch_value(V, bool) deja_vu(volume.domain());
- mln::level::fill(deja_vu, false);
+ mln_ch_value(I, bool) deja_vu;
+ initialize(deja_vu, f);
+ level::fill(deja_vu, false);
//parent
- mln_ch_value(V, P) parent(volume.domain());
+ mln_ch_value(I, P) parent(attr.domain());
{
- mln_fwd_piter(S) p(sp);
+ mln_fwd_piter(S) p(s);
for_all(p)
{
parent(p) = p;
@@ -133,32 +121,30 @@
}
}
- // UNION FIND ON VOLUME
- mln_fwd_piter(S) p(sp);
+ // UNION FIND ON ATTR
+ mln_fwd_piter(S) p(s);
mln_niter(N) n(nbh, p);
for_all(p)
{
- std::cout << p << std::endl;
- //if (volume(p) > lambda)
- // goto step2;
+ // std::cout << p << std::endl;
for_all(n)
{
- if (volume.domain().has(n) && deja_vu(n))
+ if (attr.domain().has(n) && deja_vu(n))
{
- //do_union(n, p);
- P r = find_root(parent, n);
+ P r = find_root__(parent, n);
if (r != p)
{
- std::cout << "neighb: " << n << std::endl;
- std::cout << "v(r): " << volume(r) << " v(p): " << volume(p) << " f(p): " << fused(p) << std::endl;
+ // std::cout << "neighb: " << n << std::endl;
+ // std::cout << "v(r): " << attr(r) << " v(p): "
+ // << attr(p) << " f(p): " << fused(p) << std::endl;
- //if (volume(r) != volume(p)) // r and p have different volumes
+ //if (attr(r) != attr(p)) // r and p have different attrs
// This check was wrong.
// you just fused with a minima.
- // then you fuse with a neighbor already fused that has the same volume as you
+ // then you fuse with a neighbor already fused that has the same attr as you
// a) 1 50 1
// 2 2 2
- // we don't have ( volume(r) == volume(p) ) => not fused(r)
+ // we don't have ( attr(r) == attr(p) ) => not fused(r)
// even if r and p are not minima
// problem :
@@ -166,39 +152,44 @@
// - when fusing cmpts (a) : same level, both fused. DEC
// One cmpt less if
- if (fused(r) && min_v(p) == 0) // p is not a minima
- if (fused(p)) // p already belong to a cmpt (fused for an another n)
- if (cmpts >= lambda) // union is still allowed
+
+// if (fused(r) && min_v(p) == 0) // p is not a minima
+// if (fused(p)) // p already belong to a cmpt (fused for an another n)
+// if (cmpts >= lambda) // union is still allowed
+
+ if (fused(r) && min_v(p) == 0 // p is not a minima
+ && fused(p) // p already belong to a cmpt (fused for an another n)
+ && cmpts >= lambda) // union is still allowed
{
- cmpts--;
- std::cout << "dec" << std::endl;
+ --cmpts;
+ // std::cout << "dec" << std::endl;
}
- mln_invariant(fused(r) || volume(r) == volume(p));
+ mln_invariant(fused(r) || attr(r) == attr(p));
// Union made if
if (cmpts >= lambda || // union is still allowed or
- not fused(r) || // r not fused or
- not fused(p) || // p not fused or
+ ! fused(r) || // r not fused or
+ ! fused(p) || // p not fused or
min_v(p) != 0) // p is a minima
{
- std::cout << "fuse" << p << n << std::endl;
+ // std::cout << "fusing " << p << " with " << n << std::endl;
parent(r) = p;
// This test is mandatory. Sometimes (--_) points are fused
- // tought none of these points belongs to a component (attached
+ // tough none of these points belongs to a component (attached
// to a local minima). In this case fused(p) must not be true
// since it can be fused again without removing a component.
- // looking if r is fused should be enought.
+ // looking if r is fused should be enough.
// This test force minima to be initialized fused.
if (fused(r))
fused(p) = true;
// If I try to fuse with something never fused I am on a plateau.
- // not fused(r) => ( volume(r) == volume(p) )
- mln_invariant(fused(r) || volume(r) == volume(p));
- // fused(r) and ( volume(r) == volume(p) ) happen on minima plateau.
+ // not fused(r) => ( attr(r) == attr(p) )
+ mln_invariant(fused(r) || attr(r) == attr(p));
+ // fused(r) and ( attr(r) == attr(p) ) happen on minima plateau.
// fused(n) = true; // useless ? probably yes because when we
// want to know that we really fuse component, we look at
@@ -206,7 +197,8 @@
// fused(n) is not an invariant: --_. And it is ok (I think).
// We don't have to retro-propagate fused.
- std::cerr << "volume " << volume(p) << " - " << cmpts << std::endl;
+
+ // std::cout << "attr " << attr(p) << " - " << cmpts << std::endl;
//debug::println(fused);
}
}
@@ -215,16 +207,17 @@
deja_vu(p) = true;
}
- mln_ch_value(I,value::int_u<16>) iota(ima.domain());
+ mln_ch_value(I,value::int_u<16>) iota(f.domain());
debug::iota(iota);
std::cout << std::endl;
std::cout << "cmpts : " << cmpts << std::endl;
// second pass
- I output(ima.domain());
+ mln_concrete(I) output;
+ initialize(output, f);
{
- mln_bkd_piter(S) p(sp);
+ mln_bkd_piter(S) p(s);
for_all(p)
if (parent(p) == p) // p is root.
output(p) = iota(p);
@@ -235,11 +228,36 @@
return output;
}
- } // end of namespace n_cmpt
+} // end of namespace mln
-# endif // ! MLN_INCLUDE_ONLY
-} // end of namespace mln
-#endif /* MLN_N_CMPT3_HH */
+void usage(char* argv[])
+{
+ std::cerr << "usage: " << argv[0] << " input.pgm n" << std::endl;
+ std::cerr << "n: expected number of basins" << std::endl;
+ std::abort();
+}
+
+
+int main(int argc, char* argv[])
+{
+ using namespace mln;
+ using value::int_u8;
+
+ if (argc != 3)
+ usage(argv);
+ typedef image2d<int_u8> I;
+ I f;
+ io::pgm::load(f, argv[1]);
+ debug::println("f =", f);
+
+ unsigned n = std::atoi(argv[2]);
+
+ accu::count< util::pix<I> > acc;
+ // accu::volume<I> acc;
+
+ image2d<int_u8> g = n_cmpt(acc, f, c4(), n + 1);
+ debug::println(g);
+}