* green/histo1d : New directory.
* green/histo1d/Makefile.am : New Makefile.
* green/histo1d/histo1d.hh : New C++ type.
* green/histo1d/save_sh.hh : New gnuplot export routine.
* green/histo1d/histo1d.cc : New unitary tests.
---
trunk/milena/sandbox/ChangeLog | 10 +
trunk/milena/sandbox/green/histo1d/Makefile.am | 49 +++++
trunk/milena/sandbox/green/histo1d/histo1d.cc | 274 ++++++++++++++++++++++++
trunk/milena/sandbox/green/histo1d/histo1d.hh | 270 +++++++++++++++++++++++
trunk/milena/sandbox/green/histo1d/save_sh.hh | 198 +++++++++++++++++
5 files changed, 801 insertions(+), 0 deletions(-)
create mode 100644 trunk/milena/sandbox/green/histo1d/Makefile.am
create mode 100644 trunk/milena/sandbox/green/histo1d/histo1d.cc
create mode 100644 trunk/milena/sandbox/green/histo1d/histo1d.hh
create mode 100644 trunk/milena/sandbox/green/histo1d/save_sh.hh
diff --git a/trunk/milena/sandbox/ChangeLog b/trunk/milena/sandbox/ChangeLog
index efcfd71..87880a5 100644
--- a/trunk/milena/sandbox/ChangeLog
+++ b/trunk/milena/sandbox/ChangeLog
@@ -18,6 +18,16 @@
2009-08-04 Yann Jacquelet <jacquelet(a)lrde.epita.fr>
+ Write histogram accumulator which the result is image1d.
+
+ * green/histo1d : New directory.
+ * green/histo1d/Makefile.am : New Makefile.
+ * green/histo1d/histo1d.hh : New C++ type.
+ * green/histo1d/save_sh.hh : New gnuplot export routine.
+ * green/histo1d/histo1d.cc : New unitary tests.
+
+2009-08-04 Yann Jacquelet <jacquelet(a)lrde.epita.fr>
+
Integrate LRDE code writting rules in the Stats code.
* green/Stats/Makefile.am : Remove Makefile.
diff --git a/trunk/milena/sandbox/green/histo1d/Makefile.am
b/trunk/milena/sandbox/green/histo1d/Makefile.am
new file mode 100644
index 0000000..36a83e3
--- /dev/null
+++ b/trunk/milena/sandbox/green/histo1d/Makefile.am
@@ -0,0 +1,49 @@
+#
+# Generic Makefile
+#
+
+BIN_PATTERN= trunk/build/milena
+SRC_PATTERN= trunk/milena
+
+CXXFLAGS= -ggdb -O0 -Wall -W -pedantic -ansi -pipe
+ECHO= echo
+RM= rm
+MKDIR= mkdir
+CP= cp
+
+ifeq ($(findstring $(BIN_PATTERN),$(PWD)), $(BIN_PATTERN))
+BIN_DIR=
+SRC_DIR= $(subst $(BIN_PATTERN),$(SRC_PATTERN), $(PWD))/
+else
+BIN_DIR= $(subst $(SRC_PATTERN),$(BIN_PATTERN), $(PWD))/
+SRC_DIR=
+endif
+
+TARGET= $(BIN_DIR)$(notdir $(PWD))
+BIN_MAKE= $(BIN_DIR)Makefile
+SRC_MAKE= $(SRC_DIR)Makefile.am
+
+
+SRC_FILES= $(wildcard $(SRC_DIR)*.cc)
+OLD_FILES= $(addsuffix ~, $(SRC_FILES))
+OBJ_FILES= $(addprefix $(BIN_DIR), $(notdir $(SRC_FILES:%.cc=%.o)))
+
+
+all: $(BIN_DIR) $(TARGET)
+ @$(ECHO) "Compilation terminée"
+
+$(BIN_DIR):
+ $(MKDIR) $(BIN_DIR)
+ $(CP) $(SRC_MAKE) $(BIN_MAKE)
+
+$(TARGET):$(OBJ_FILES)
+ $(LINK.cc) $^ $(LOADLIBES) $(LDLIBS) -o $@
+
+$(BIN_DIR)%.o:$(SRC_DIR)%.cc
+ $(COMPILE.cc) $(OUTPUT_OPTION) $<
+
+clean:
+ -@$(RM) $(TARGET)
+ -@$(RM) $(OBJ_FILES)
+ -@$(RM) $(OLD_FILES)
+
diff --git a/trunk/milena/sandbox/green/histo1d/histo1d.cc
b/trunk/milena/sandbox/green/histo1d/histo1d.cc
new file mode 100644
index 0000000..c39a412
--- /dev/null
+++ b/trunk/milena/sandbox/green/histo1d/histo1d.cc
@@ -0,0 +1,274 @@
+/// TEST HISTO1D
+
+#include "save_sh.hh"
+#include "histo1d.hh"
+
+#include <mln/io/pgm/load.hh>
+#include <mln/io/plot/save.hh>
+
+#include <mln/data/compute.hh>
+
+#include <mln/value/int_u8.hh>
+#include <mln/value/label_8.hh>
+
+#include <mln/core/alias/neighb1d.hh>
+#include <mln/core/alias/box1d.hh>
+#include <mln/core/alias/point1d.hh>
+
+#include <mln/core/routine/initialize.hh>
+#include <mln/core/contract.hh>
+
+#include <mln/accu/math/sum.hh>
+#include <mln/accu/math/count.hh>
+#include <mln/accu/stat/mean.hh>
+#include <mln/accu/stat/variance.hh>
+
+#include <mln/morpho/watershed/flooding.hh>
+#include <mln/morpho/elementary/dilation.hh>
+#include <mln/morpho/elementary/closing.hh>
+
+void test_operator_equal()
+{
+ using namespace mln::accu::stat;
+
+ typedef mln::value::int_u8 int_u8;
+ mln::accu::stat::histo1d<int_u8> histo1;
+ mln::accu::stat::histo1d<int_u8> histo2;
+ int_u8 val = 3;
+
+ histo1.init();
+ histo2.init();
+
+ mln_assertion(histo1 == histo2);
+
+ histo1.take(val);
+
+ mln_assertion(!(histo1 == histo2));
+
+ histo2.take(val);
+
+ mln_assertion(histo1 == histo2);
+
+ std::cout << "histo == histo : ok" << std::endl;
+}
+
+void test_instantiation_without_argument()
+{
+ typedef mln::value::int_u8 int_u8;
+ const mln::accu::stat::histo1d<int_u8> histo;
+ const mln::image1d<unsigned>& res = histo.to_result();
+ const mln::point1d& min = mln::point1d(mln_min(int_u8));
+ const mln::point1d& max = mln::point1d(mln_max(int_u8));
+ const mln::box1d& ref = mln::box1d(min, max);
+
+ mln_assertion(ref == res.domain());
+ mln_assertion(res.is_valid());
+
+ std::cout << "histo<T> histo : ok" << std::endl;
+}
+
+
+void test_initialization()
+{
+ typedef mln::value::int_u8 int_u8;
+ mln::accu::stat::histo1d<int_u8> histo;
+ mln::image1d<unsigned> img_res = histo.to_result();
+ mln::image1d<unsigned> img_ref;
+
+ mln::initialize(img_ref, img_res);
+ mln::data::fill(img_ref, 0);
+ histo.init();
+
+ unsigned res = mln::data::compute(mln::accu::math::sum<int_u8>(), img_res);
+ unsigned ref = mln::data::compute(mln::accu::math::sum<int_u8>(), img_ref);
+
+ mln_assertion(ref == res);
+
+ std::cout << "histo.init() : ok" << std::endl;
+}
+
+
+void test_take_argument()
+{
+ typedef mln::value::int_u8 int_u8;
+ mln::accu::stat::histo1d<int_u8> histo1;
+ mln::accu::stat::histo1d<int_u8> histo2;
+ int_u8 val = 3;
+
+ histo1.init();
+ histo2.init();
+ histo1.take(val);
+
+ const mln::image1d<unsigned> img1 = histo1.to_result();
+ const mln::image1d<unsigned> img2 = histo2.to_result();
+
+ const unsigned res = mln::data::compute(mln::accu::math::sum<int_u8>(), img1);
+ const unsigned ref = mln::data::compute(mln::accu::math::sum<int_u8>(), img2);
+
+ mln_assertion(ref == res-1);
+ mln_assertion(1 == img1(mln::point1d(val)));
+
+ std::cout << "histo.take(argument) : ok" << std::endl;
+}
+
+
+void test_take_other()
+{
+ typedef mln::value::int_u8 int_u8;
+ mln::accu::stat::histo1d<int_u8> histo1;
+ mln::accu::stat::histo1d<int_u8> histo2;
+ mln::accu::stat::histo1d<int_u8> histo3;
+ int_u8 val = 3;
+
+ histo1.init();
+ histo2.init();
+ histo3.init();
+
+ histo1.take(val);
+ histo1.take(val);
+ histo3.take(val);
+ histo2.take(val);
+ histo2.take(histo3);
+
+ mln_assertion(histo1 == histo2);
+
+ std::cout << "histo.take(other) : ok" << std::endl;
+}
+
+double count_histo(mln::image1d<unsigned> img)
+{
+ mln_precondition(img.is_valid());
+
+ double result = 0.0;
+ mln_piter_(mln::image1d<unsigned>) p(img.domain());
+
+ for_all(p)
+ result += img(p);
+
+ return result;
+}
+
+double mean_histo(mln::image1d<unsigned> img)
+{
+ mln_precondition(img.is_valid());
+
+ double count = 0.0;
+ double sum = 0.0;
+ double result = 0.0;
+ mln_piter_(mln::image1d<unsigned>) p(img.domain());
+
+ for_all(p)
+ {
+ count += img(p);
+ sum += p[0] * img(p);
+ }
+
+ result = sum / count;
+
+ return result;
+}
+
+
+double var_histo(mln::image1d<unsigned> img)
+{
+ mln_precondition(img.is_valid());
+
+ double count = 0.0;
+ double sum = 0.0;
+ double sum2 = 0.0;
+ double result = 0.0;
+ mln_piter_(mln::image1d<unsigned>) p(img.domain());
+
+ for_all(p)
+ {
+ count += img(p);
+ sum += p[0] * img(p);
+ sum2 += p[0] * p[0] * img(p);
+ }
+
+ result = sum2 / count - (sum / count) * (sum / count);
+
+ return result;
+}
+
+void test_integration()
+{
+ typedef mln::value::int_u8 int_u8;
+ typedef mln::accu::math::count<double> count;
+ typedef mln::accu::math::sum<double> sum;
+ typedef mln::accu::stat::mean<double> mean;
+ typedef mln::accu::stat::variance<double> variance;
+
+ mln::image2d<int_u8> img_ref;
+ mln::image1d<unsigned> img_res;
+
+ mln::io::pgm::load(img_ref, "/usr/local/share/olena/images/lena.pgm");
+
+ const double count_ref = mln::data::compute(count(), img_ref);
+ const double mean_ref = mln::data::compute(mean(), img_ref);
+ const double var_ref = mln::data::compute(variance(), img_ref);
+
+ img_res = mln::data::compute(mln::accu::stat::histo1d<int_u8>(), img_ref);
+
+ const double count_res = count_histo(img_res);
+ const double mean_res = mean_histo(img_res);
+ const double var_res = var_histo(img_res);
+
+ mln_assertion(count_ref == count_res);
+ mln_assertion( mean_ref == mean_res );
+ mln_assertion( var_ref == var_res );
+
+ std::cout << "test integration : ok" << std::endl;
+}
+
+
+void test_classifying()
+{
+ typedef mln::value::int_u8 int_u8;
+ typedef mln::value::label_8 label_8;
+
+ mln::image2d<int_u8> img_ref;
+ mln::image1d<unsigned> img_res;
+ mln::image1d<label_8> labels;
+ label_8 n_shape;
+
+ mln::io::pgm::load(img_ref, "/usr/local/share/olena/images/lena.pgm");
+
+ img_res = mln::data::compute(mln::accu::stat::histo1d<int_u8>(), img_ref);
+
+ mln::io::plot::save_sh(img_res, "histo.sh");
+
+ img_res = mln::morpho::elementary::closing(img_res, mln::c2());
+ img_res = mln::morpho::elementary::closing(img_res, mln::c2());
+ img_res = mln::morpho::elementary::closing(img_res, mln::c2());
+
+ mln::io::plot::save_sh(img_res, "histo1.sh");
+ /*
+ labels = mln::morpho::watershed::flooding(img_res, mln::c2(), n_shape);
+
+ mln::io::plot::save_sh(labels, "histo2.sh");
+
+ labels = mln::morpho::elementary::dilation(labels, mln::c2());
+
+ mln::io::plot::save_sh(labels, "histo3.sh");
+
+ //mln::io::plot::save(labels, "labelized.data");
+ */
+}
+
+int main()
+{
+ using namespace mln;
+ using namespace std;
+
+ test_instantiation_without_argument();
+ test_initialization();
+ test_take_argument();
+ test_take_other();
+ test_operator_equal();
+ test_integration();
+
+ //test_classifying();
+
+ return 0;
+}
diff --git a/trunk/milena/sandbox/green/histo1d/histo1d.hh
b/trunk/milena/sandbox/green/histo1d/histo1d.hh
new file mode 100644
index 0000000..23e230b
--- /dev/null
+++ b/trunk/milena/sandbox/green/histo1d/histo1d.hh
@@ -0,0 +1,270 @@
+// Copyright (C) 2007 EPITA Research and Development Laboratory (LRDE)
+// Copyright (C) 2008 EPITA Research and Development Laboratory (LRDE)
+// Copyright (C) 2009 EPITA Research and Development Laboratory (LRDE)
+//
+// This file is part of Olena.
+//
+// Olena is free software: you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation, version 2 of the License.
+//
+// Olena 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 Olena. If not, see <http://www.gnu.org/licenses/>.
+//
+// As a special exception, you may use this file as part of a free
+// software project without restriction. Specifically, if other files
+// instantiate templates or use macros or inline functions from this
+// file, or you compile this file and link it with other files to produce
+// an executable, this file does not by itself cause the resulting
+// executable to be covered by the GNU General Public License. This
+// exception does not however invalidate any other reasons why the
+// executable file might be covered by the GNU General Public License.
+
+#ifndef MLN_ACCU_HISTO1D_HH
+#define MLN_ACCU_HISTO1D_HH
+
+/// \file
+///
+/// \brief Define an histogram as an accumulator which returns an image1d .
+///
+/// It based on image to allow collecting statistics on it.
+///
+
+#include <iostream>
+
+#include <mln/accu/internal/base.hh>
+
+#include <mln/core/macros.hh>
+#include <mln/core/image/image1d.hh>
+
+#include <mln/trait/value/comp.hh>
+
+#include <mln/arith/plus.hh>
+
+#include <mln/trace/entering.hh>
+#include <mln/trace/exiting.hh>
+
+#include <mln/value/ops.hh>
+
+namespace mln
+{
+
+ namespace accu
+ {
+
+ namespace stat
+ {
+
+ // Forward declaration
+ template <typename V>
+ struct histo1d;
+
+ } // end of namespace mln::accu::stat
+
+ } // end of namespace mln::accu
+
+
+ namespace trait
+ {
+
+ template <typename V>
+ struct accumulator_< mln::accu::stat::histo1d<V> >
+ {
+ typedef accumulator::has_untake::no has_untake;
+ typedef accumulator::has_set_value::no has_set_value;
+ typedef accumulator::has_stop::no has_stop;
+ typedef accumulator::when_pix::use_v when_pix;
+ };
+
+ template <typename V>
+ struct set_precise_binary_<op::eq,
+ accu::stat::histo1d<V>,
+ accu::stat::histo1d<V> >
+ {
+ typedef bool ret;
+ };
+
+ } // end of namespace mln::trait
+
+ namespace accu
+ {
+
+ namespace stat
+ {
+
+
+ /// \brief Define an histogram which returns an image1d .
+ ///
+ /// Param V defines the space in which we count the values.
+ /// For instance, this histogram works image2d<gl8> or image1d<gl16>.
+ /// The histogram count the occurrence of each value.
+ ///
+ /// \ingroup modaccuvalues
+
+ template <typename V>
+ struct histo1d :
+ public mln::accu::internal::base<image1d<unsigned>, histo1d<V> >
+ {
+ typedef V argument;
+ typedef image1d<unsigned> result;
+ typedef result q_result;
+
+ /// Constructors
+ /// \{
+ /// \brief Nothing to do
+ histo1d();
+ /// \}
+
+
+ /// Manipulators.
+ /// \{
+ /// \brief Initialize the bounding box of the resulting image.
+ void init();
+
+
+ /// \brief Update the histogram with the RGB pixel t.
+ /// \param[in] t a RGB pixel.
+ void take(const argument& t);
+
+
+ /// \brief Update the histogram with an other histogram.
+ /// \param[in] other the other histogram.
+ void take(const histo1d<V>& other);
+ /// \}
+
+ /// Accessors.
+ /// \{
+ result to_result() const;
+ operator result () const;
+ /// \}
+
+ /// Check whethever this accumulator is able to return a result.
+ /// Always in a safe state and then always return true;
+ bool is_valid() const;
+
+ protected:
+ result count_;
+ };
+
+ template <typename V>
+ bool operator==(const histo1d<V>& histo1, const histo1d<V>&
histo2);
+
+#ifndef MLN_INCLUDE_ONLY
+
+
+
+
+ template <typename V>
+ inline
+ histo1d<V>::histo1d()
+ {
+ trace::entering("mln::accu::stat::histo1d<V>::histo1d");
+ typedef mln_trait_value_comp(V,0) comp;
+
+ count_.init_(box1d(point1d(mln_min(comp)), // -> 0
+ point1d(mln_max(comp)))); // -> 2^n-1
+
+ trace::exiting("mln::accu::stat::histo1d<V>::histo1d");
+ }
+
+ template <typename V>
+ inline
+ void histo1d<V>::init()
+ {
+ trace::entering("mln::accu::stat::histo1d<V>::init");
+
+ data::fill(count_, 0);
+ trace::exiting("mln::accu::stat::histo1d<V>::init");
+ }
+
+ template <typename V>
+ inline
+ void histo1d<V>::take(const argument& t)
+ {
+ trace::entering("mln::accu::stat::histo1d<V>::take");
+
+ ++count_(point1d(t));
+
+ trace::exiting("mln::accu::stat::histo1d<V>::take");
+ }
+
+
+ template <typename V>
+ inline
+ void histo1d<V>::take(const histo1d<V>& other)
+ {
+ trace::entering("mln::accu::stat::histo1d<V>::take");
+
+ count_ += other.count_;
+
+ trace::exiting("mln::accu::stat::histo1d<V>::take");
+ }
+
+ template <typename V>
+ inline
+ typename histo1d<V>::result histo1d<V>::to_result() const
+ {
+ trace::entering("mln::accu::stat::histo1d<V>::to_result");
+
+ trace::exiting("mln::accu::stat::histo1d<V>::to_result");
+ return count_;
+ }
+
+ template <typename V>
+ inline
+ histo1d<V>::operator result() const
+ {
+ trace::entering("mln::accu::stat::histo1d<V>::operator result");
+
+ trace::exiting("mln::accu::stat::histo1d<V>::operator result");
+ return count_;
+ }
+
+ template <typename V>
+ inline
+ bool histo1d<V>::is_valid() const
+ {
+ trace::entering("mln::accu::stat::histo1d<V>::is_valid");
+
+ trace::exiting("mln::accu::stat::histo1d<V>::is_valid");
+ return true;
+ }
+
+ template <typename V>
+ bool operator==(const histo1d<V>& histo1, const histo1d<V>&
histo2)
+ {
+ trace::entering("mln::accu::stat::operator==");
+
+ bool result = true;
+ const image1d<unsigned>& res1 = histo1.to_result();
+ const image1d<unsigned>& res2 = histo2.to_result();
+
+ mln_precondition(res1.is_valid());
+ mln_precondition(res2.is_valid());
+
+ mln_piter(image1d<unsigned>) p1(res1.domain());
+ mln_piter(image1d<unsigned>) p2(res2.domain());
+
+ for_all_2(p1, p2)
+ result &= (res1(p1) == res2(p2));
+
+ trace::exiting("mln::accu::stat::operator==");
+ return result;
+ }
+
+
+#endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace mln::accu::stat
+
+ } // end of namespace mln::accu
+
+} // end of namespace mln
+
+#endif // ! MLN_ACCU_HISTO1D_HH
diff --git a/trunk/milena/sandbox/green/histo1d/save_sh.hh
b/trunk/milena/sandbox/green/histo1d/save_sh.hh
new file mode 100644
index 0000000..ece30f4
--- /dev/null
+++ b/trunk/milena/sandbox/green/histo1d/save_sh.hh
@@ -0,0 +1,198 @@
+// Copyright (C) 2007 EPITA Research and Development Laboratory (LRDE)
+// Copyright (C) 2008 EPITA Research and Development Laboratory (LRDE)
+// Copyright (C) 2009 EPITA Research and Development Laboratory (LRDE)
+//
+// This file is part of Olena.
+//
+// Olena is free software: you can redistribute it and/or modify it under
+// the terms of the GNU General Public License as published by the Free
+// Software Foundation, version 2 of the License.
+//
+// Olena 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 Olena. If not, see <http://www.gnu.org/licenses/>.
+//
+// As a special exception, you may use this file as part of a free
+// software project 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_IO_PLOT_SAVE_SH_HH
+#define MLN_IO_PLOT_SAVE_SH_HH
+
+/// \file
+///
+/// \brief Define some function to export to gnuplots format as a script shell.
+///
+/// Theses routines help to visualize data.
+///
+
+#include <fstream>
+#include <string>
+
+#include <mln/core/macros.hh>
+#include <mln/core/image/image1d.hh>
+#include <mln/core/image/image2d.hh>
+#include <mln/core/image/image3d.hh>
+
+
+namespace mln
+{
+
+ namespace io
+ {
+
+ namespace plot
+ {
+
+ /// \brief Save a image1d as a gnuplot script shell.
+ /// \param[in] img the 1d image which contains the data to save.
+ /// \param[in] filename the name of the unix script shell.
+ template <typename I>
+ void save_sh(const image1d<I>& img, const std::string& filename);
+
+ /// \brief Save a image2d as a gnuplot script shell.
+ /// \param[in] img the 2d image which contains the data to save.
+ /// \param[in] filename the name of the unix script shell.
+ template <typename I>
+ void save_sh(const image2d<I>& img, const std::string& filename);
+
+ /// \brief Save a image3d as a gnuplot script shell.
+ /// \param[in] img the 3d image which contains the data to save.
+ /// \param[in] filename the name of the unix script shell.
+ template <typename I>
+ void save_sh(const image3d<I>& img, const std::string& filename);
+
+ } // end of namespace mln::accu::stat
+
+ } // end of namespace mln::accu
+
+
+ namespace io
+ {
+
+ namespace plot
+ {
+
+#ifndef MLN_INCLUDE_ONLY
+
+ template <typename I>
+ inline
+ void save_sh(const image1d<I>& img, const std::string& filename)
+ {
+ trace::entering("mln::io::plot::save_sh<1d>");
+ mln_precondition(img.is_valid());
+
+ std::ofstream out(filename.c_str());
+ mln_piter(image1d<I>) p(img.domain());
+
+ out << "#!/bin/sh" << std::endl;
+ out << "##########################" << std::endl;
+ out << "# Two columns = (x,data) #" << std::endl;
+ out << "##########################" << std::endl;
+ out << std::endl;
+ out << "gnuplot <<EOF" <<
std::endl;
+ out << "set terminal x11 persist 1" << std::endl;
+ //out << "plot '-' with points pointtype 0" <<
std::endl;
+ out << "plot '-' with histograms" << std::endl;
+
+ for_all(p)
+ {
+ // for (unsigned i = 0; i < mln_dim(I); ++i)
+ // out << p[0] << " ";
+
+ out << img(p) << std::endl;
+ }
+ out << "e" << std::endl;
+ out << "EOF" << std::endl;
+
+ out.close();
+ trace::exiting("mln::io::plot::save_sh<1d>");
+ }
+
+ template <typename I>
+ inline
+ void save_sh(const image2d<I>& img, const std::string& filename)
+ {
+ trace::entering("mln::io::plot::save_sh<2d>")
+ mln_precondition(img.is_valid());
+
+ std::ofstream out(filename.c_str());
+ mln_piter(I) p(img.domain());
+
+ out << "#!/bin/sh" << std::endl;
+ out << "##############################" << std::endl;
+ out << "# Three columns = (x,y,data) #" << std::endl;
+ out << "##############################" << std::endl;
+ out << std::endl;
+ out << "gnuplot <<EOF" <<
std::endl;
+ out << "set terminal x11 persist 1" << std::endl;
+ out << "plot '-' with points palette pointtype 0" <<
std::endl;
+
+ for_all(p)
+ {
+ for (unsigned i = 0; i < mln_dim(I); ++i)
+ out << p << " ";
+
+ out << img(p) << std::endl;
+ }
+
+ out << "e" << std::endl;
+ out << "EOF" << std::endl;
+
+ out.close();
+ trace::exiting("mln::io::plot::save_sh<2d>");
+ }
+
+ template <typename I>
+ inline
+ void save_sh(const image3d<I>& img, const std::string& filename)
+ {
+ trace::entering("mln::io::plot::save_sh<3d>")
+ mln_precondition(img.is_valid());
+
+ std::ofstream out(filename.c_str());
+ mln_piter(I) p(img.domain());
+
+ out << "#!/bin/sh" << std::endl;
+ out << "####################################" << std::endl;
+ out << "# Columns = (red,green,blue,count) #" << std::endl;
+ out << "####################################" << std::endl;
+ out << std::endl;
+ out << "gnuplot <<EOF" <<
std::endl;
+ out << "set terminal x11 persist 1" << std::endl;
+ out << "splot '-' with points palette pointtype 0" <<
std::endl;
+
+ for_all(p)
+ if (0 < img(p))
+ {
+ out << p.row() << " ";
+ out << p.col() << " ";
+ out << p.sli() << " ";
+ out << img(p) << std::endl;
+ }
+ out << "e" << std::endl;
+ out << "EOF" << std::endl;
+
+ out.close();
+ trace::exiting("mln::io::plot::save_sh<3d>");
+ }
+
+#endif // ! MLN_INCLUDE_ONLY
+
+
+ } // end of namespace mln::accu::stat
+
+ } // end of namespace mln::accu
+
+} // end of namespace mln
+
+#endif // ! MLN_IO_PLOT_SAVE_SH_HH
--
1.5.6.5