olena-2.0-118-g0cd712a Add Singh algorithm.

* scribo/binarization/internal/singh_formula.hh, * scribo/binarization/internal/singh_functor.hh, * scribo/binarization/singh.hh, * src/binarization/singh.cc: New. --- scribo/ChangeLog | 9 +++ .../{sauvola_formula.hh => singh_formula.hh} | 55 +++++++++---------- .../{niblack_functor_fast.hh => singh_functor.hh} | 36 +++++++------ .../scribo/binarization/{niblack.hh => singh.hh} | 39 +++++++------- scribo/src/binarization/{wolf.cc => singh.cc} | 11 ++-- 5 files changed, 79 insertions(+), 71 deletions(-) copy scribo/scribo/binarization/internal/{sauvola_formula.hh => singh_formula.hh} (58%) copy scribo/scribo/binarization/internal/{niblack_functor_fast.hh => singh_functor.hh} (81%) copy scribo/scribo/binarization/{niblack.hh => singh.hh} (71%) copy scribo/src/binarization/{wolf.cc => singh.cc} (90%) diff --git a/scribo/ChangeLog b/scribo/ChangeLog index 608254b..5147cf4 100644 --- a/scribo/ChangeLog +++ b/scribo/ChangeLog @@ -1,5 +1,14 @@ 2012-08-22 Guillaume Lazzara <z@lrde.epita.fr> + Add Singh algorithm. + + * scribo/binarization/internal/singh_formula.hh, + * scribo/binarization/internal/singh_functor.hh, + * scribo/binarization/singh.hh, + * src/binarization/singh.cc: New. + +2012-08-22 Guillaume Lazzara <z@lrde.epita.fr> + Make the area value depends on the first scale ratio. * scribo/binarization/sauvola_ms.hh: Change area ranges. diff --git a/scribo/scribo/binarization/internal/sauvola_formula.hh b/scribo/scribo/binarization/internal/singh_formula.hh similarity index 58% copy from scribo/scribo/binarization/internal/sauvola_formula.hh copy to scribo/scribo/binarization/internal/singh_formula.hh index 005c034..e307a2c 100644 --- a/scribo/scribo/binarization/internal/sauvola_formula.hh +++ b/scribo/scribo/binarization/internal/singh_formula.hh @@ -1,5 +1,4 @@ -// Copyright (C) 2011, 2012 EPITA Research and Development Laboratory -// (LRDE) +// Copyright (C) 2012 EPITA Research and Development Laboratory (LRDE) // // This file is part of Olena. // @@ -24,31 +23,25 @@ // exception does not however invalidate any other reasons why the // executable file might be covered by the GNU General Public License. -#ifndef SCRIBO_BINARIZATION_INTERNAL_SAUVOLA_FORMULA_HH -# define SCRIBO_BINARIZATION_INTERNAL_SAUVOLA_FORMULA_HH +#ifndef SCRIBO_BINARIZATION_INTERNAL_SINGH_FORMULA_HH +# define SCRIBO_BINARIZATION_INTERNAL_SINGH_FORMULA_HH /// \file /// -/// \brief Routines computing a threshold using Sauvola's binarization +/// \brief Routines computing a threshold using Singh's binarization /// formula. -// Setup default Sauvola's formula parameters values. -// These macros may be used in other variant of Sauvola's algorithms. -// -// Values are set according to the following reference: "Automatic -// Evaluation of Document Binarization Results", Badekas and al, 2005 -// -// Badekas et al. said 0.34 was best for Sauvola. -# define SCRIBO_DEFAULT_SAUVOLA_K 0.34 -// -// 128 is best for grayscale documents. -# define SCRIBO_DEFAULT_SAUVOLA_R 128 +// Setup default Singh's formula parameters values. +// These macros may be used in other variant of Singh's algorithms. +# define SCRIBO_DEFAULT_SINGH_K 0.06 #include <mln/core/alias/point2d.hh> +// extern mln::image2d<bool> skewness_pbm; + namespace scribo { @@ -60,10 +53,11 @@ namespace scribo using namespace mln; - struct sauvola_formula + template <typename V> + struct singh_formula { - /*! \brief Compute a threshold using Sauvola's formula. + /*! \brief Compute a threshold using Singh's formula. \param[in] m_x_y Mean value. \param[in] s_x_y Standard deviation. @@ -75,33 +69,36 @@ namespace scribo \return A threshold. */ - double operator()(const double m_x_y, const double s_x_y, - const double K, const double R) const; + double operator()(const V& v, const double m_x_y, const double K) const; /*! - \overload K = 0.34 and R = 128. + \overload K = 0.34. */ - double operator()(const double m_x_y, const double s_x_y) const; + double operator()(const V& v, const double m_x_y) const; }; # ifndef MLN_INCLUDE_ONLY + // bool b; + // double skewness_; + + template <typename V> inline double - sauvola_formula::operator()(const double m_x_y, const double s_x_y, - const double K, const double R) const + singh_formula<V>::operator()(const V& v, const double m_x_y, const double K) const { - return m_x_y * (1.0 + K * ((s_x_y / R) - 1.0)); + double mean_dev = v - m_x_y; + return m_x_y * (1.0 + K * (mean_dev / (1 - mean_dev) - 1)); } + template <typename V> inline double - sauvola_formula::operator()(const double m_x_y, const double s_x_y) const + singh_formula<V>::operator()(const V& v, const double m_x_y) const { - return (*this)(m_x_y, s_x_y, - SCRIBO_DEFAULT_SAUVOLA_K, SCRIBO_DEFAULT_SAUVOLA_R); + return (*this)(v, m_x_y, SCRIBO_DEFAULT_SINGH_K); } # endif // ! MLN_INCLUDE_ONLY @@ -112,4 +109,4 @@ namespace scribo } // end of namespace scribo -#endif // ! SCRIBO_BINARIZATION_INTERNAL_SAUVOLA_FORMULA_HH +#endif // ! SCRIBO_BINARIZATION_INTERNAL_SINGH_FORMULA_HH diff --git a/scribo/scribo/binarization/internal/niblack_functor_fast.hh b/scribo/scribo/binarization/internal/singh_functor.hh similarity index 81% copy from scribo/scribo/binarization/internal/niblack_functor_fast.hh copy to scribo/scribo/binarization/internal/singh_functor.hh index 8251ecd..5e7e66f 100644 --- a/scribo/scribo/binarization/internal/niblack_functor_fast.hh +++ b/scribo/scribo/binarization/internal/singh_functor.hh @@ -23,18 +23,18 @@ // exception does not however invalidate any other reasons why the // executable file might be covered by the GNU General Public License. -#ifndef SCRIBO_BINARIZATION_INTERNAL_NIBLACK_FUNCTOR_FAST_HH -# define SCRIBO_BINARIZATION_INTERNAL_NIBLACK_FUNCTOR_FAST_HH +#ifndef SCRIBO_BINARIZATION_INTERNAL_SINGH_FUNCTOR_HH +# define SCRIBO_BINARIZATION_INTERNAL_SINGH_FUNCTOR_HH /// \file /// -/// \todo Refactor with sauvola_functor. +/// # include <mln/core/image/image2d.hh> # include <mln/core/alias/neighb2d.hh> # include <mln/extension/fill.hh> -# include <scribo/binarization/internal/niblack_formula.hh> +# include <scribo/binarization/internal/singh_formula.hh> # ifdef SCRIBO_LOCAL_THRESHOLD_DEBUG # include <scribo/binarization/internal/local_threshold_debug.hh> @@ -54,9 +54,9 @@ namespace scribo template <typename I> - struct niblack_functor_fast + struct singh_functor { - niblack_functor_fast(const Image<I>& input, double K); + typedef mln_value(I) V; // Moves in input and output images are made using "step" // pixels. It corresponds to the scale ratio between the input @@ -64,6 +64,8 @@ namespace scribo // values. enum { step = 3 }; + singh_functor(const Image<I>& input, double K); + // Run every 4 pixels. void exec(double mean, double stddev); @@ -75,12 +77,12 @@ namespace scribo const I input; mln_ch_value(I,bool) output; - const mln_value(I)* pi; + const V* pi; bool* po; double K_; - scribo::binarization::internal::niblack_formula formula_; + scribo::binarization::internal::singh_formula<V> formula_; unsigned next_line3; unsigned offset1; @@ -90,8 +92,7 @@ namespace scribo #ifndef MLN_INCLUDE_ONLY template <typename I> - niblack_functor_fast<I>::niblack_functor_fast(const Image<I>& input_, - double K) + singh_functor<I>::singh_functor(const Image<I>& input_, double K) : input(exact(input_)), pi(&input(input.domain().pmin())), K_(K) @@ -116,14 +117,18 @@ namespace scribo template <typename I> void - niblack_functor_fast<I>::exec(double mean, double stddev) + singh_functor<I>::exec(double mean, double stddev) { - double th = formula_(mean, stddev, K_); + (void) stddev; + for (int i = 0; i < step; ++i, ++po, ++pi) { + double th = formula_(*pi, mean, K_); *po = (*pi <= th); + th = formula_(*(pi + offset1), mean, K_); *(po + offset1) = (*(pi + offset1) <= th); + th = formula_(*(pi + offset2), mean, K_); *(po + offset2) = (*(pi + offset2) <= th); } @@ -132,7 +137,6 @@ namespace scribo unsigned index = pi - input.buffer(); debug_mean.element(index) = mean * mean_debug_factor; - debug_stddev.element(index) = stddev * stddev_debug_factor; debug_threshold.element(index) = th; # endif // ! SCRIBO_LOCAL_THRESHOLD_DEBUG @@ -140,7 +144,7 @@ namespace scribo template <typename I> void - niblack_functor_fast<I>::end_of_row(int) + singh_functor<I>::end_of_row(int) { po += next_line3; pi += next_line3; @@ -148,7 +152,7 @@ namespace scribo template <typename I> void - niblack_functor_fast<I>::finalize() + singh_functor<I>::finalize() { } @@ -160,4 +164,4 @@ namespace scribo } // end of namespace scribo -#endif // SCRIBO_BINARIZATION_INTERNAL_NIBLACK_FUNCTOR_FAST_HH +#endif // SCRIBO_BINARIZATION_INTERNAL_SINGH_FUNCTOR_HH diff --git a/scribo/scribo/binarization/niblack.hh b/scribo/scribo/binarization/singh.hh similarity index 71% copy from scribo/scribo/binarization/niblack.hh copy to scribo/scribo/binarization/singh.hh index 134e15a..58f4664 100644 --- a/scribo/scribo/binarization/niblack.hh +++ b/scribo/scribo/binarization/singh.hh @@ -1,5 +1,4 @@ -// Copyright (C) 2009, 2010, 2011 EPITA Research and Development -// Laboratory (LRDE) +// Copyright (C) 2012 EPITA Research and Development Laboratory (LRDE) // // This file is part of Olena. // @@ -24,15 +23,15 @@ // exception does not however invalidate any other reasons why the // executable file might be covered by the GNU General Public License. -#ifndef SCRIBO_BINARIZATION_NIBLACK_HH -# define SCRIBO_BINARIZATION_NIBLACK_HH +#ifndef SCRIBO_BINARIZATION_SINGH_HH +# define SCRIBO_BINARIZATION_SINGH_HH /// \file /// /// # include <mln/core/concept/image.hh> -# include <scribo/binarization/internal/niblack_functor.hh> +# include <scribo/binarization/internal/singh_functor.hh> # include <scribo/binarization/internal/local_threshold_core.hh> namespace scribo @@ -48,21 +47,20 @@ namespace scribo \input[in] input An image. \input[in] window_size The window size. - \input[in] K Sauvola's formulae constant. + \input[in] K Singh's formulae constant. \return A binary image. */ template <typename I> mln_ch_value(I, bool) - niblack(const Image<I>& input, unsigned window_size, double K); + singh(const Image<I>& input, unsigned window_size, double K); /*! \brief Convert an image into a binary image. - Sauvola's formulae constant K is set to - SCRIBO_DEFAULT_NIBLACK_K. + Singh's formulae constant K is set to 0.34. \input[in] input An image. \input[in] window_size The window size. @@ -72,7 +70,7 @@ namespace scribo */ template <typename I> mln_ch_value(I, bool) - niblack(const Image<I>& input, unsigned window_size); + singh(const Image<I>& input, unsigned window_size); /// \overload @@ -80,7 +78,7 @@ namespace scribo // template <typename I> mln_ch_value(I, bool) - niblack(const Image<I>& input); + singh(const Image<I>& input); # ifndef MLN_INCLUDE_ONLY @@ -89,35 +87,36 @@ namespace scribo template <typename I> mln_ch_value(I, bool) - niblack(const Image<I>& input, unsigned window_size, double K) + singh(const Image<I>& input, unsigned window_size, double K) { - trace::entering("scribo::binarization::niblack"); + trace::entering("scribo::binarization::singh"); mln_precondition(exact(input).is_valid()); - internal::niblack_functor<I> f(input, K); + internal::singh_functor<I> f(input, K); internal::local_threshold_core(input, f, window_size); - trace::exiting("scribo::binarization::niblack"); + trace::exiting("scribo::binarization::singh"); return f.output; } template <typename I> mln_ch_value(I, bool) - niblack(const Image<I>& input, unsigned window_size) + singh(const Image<I>& input, unsigned window_size) { - return niblack(input, window_size, SCRIBO_DEFAULT_NIBLACK_K); + return singh(input, window_size, SCRIBO_DEFAULT_SINGH_K); } template <typename I> mln_ch_value(I, bool) - niblack(const Image<I>& input) + singh(const Image<I>& input) { - return niblack(input, 11); + return singh(input, 11); } + # endif // ! MLN_INCLUDE_ONLY @@ -126,4 +125,4 @@ namespace scribo } // end of namespace scribo -#endif // ! SCRIBO_BINARIZATION_NIBLACK_HH +#endif // ! SCRIBO_BINARIZATION_SINGH_HH diff --git a/scribo/src/binarization/wolf.cc b/scribo/src/binarization/singh.cc similarity index 90% copy from scribo/src/binarization/wolf.cc copy to scribo/src/binarization/singh.cc index 4495f64..8078bfd 100644 --- a/scribo/src/binarization/wolf.cc +++ b/scribo/src/binarization/singh.cc @@ -1,5 +1,4 @@ -// Copyright (C) 2009, 2010, 2011, 2012 EPITA Research and Development -// Laboratory (LRDE) +// Copyright (C) 2012 EPITA Research and Development Laboratory (LRDE) // // This file is part of Olena. // @@ -31,7 +30,7 @@ #include <mln/data/transform.hh> #include <mln/fun/v2v/rgb_to_luma.hh> -#include <scribo/binarization/wolf.hh> +#include <scribo/binarization/singh.hh> #include <scribo/debug/option_parser.hh> #include <scribo/debug/logger.hh> @@ -57,10 +56,10 @@ static const scribo::debug::opt_data opt_desc[] = // name, description, arguments, check args function, number of args, default arg { "debug-prefix", "Enable debug image outputs. Prefix image name with that " "given prefix.", "<prefix>", 0, 1, 0 }, - { "k", "Wolf's formulae parameter", "<value>", 0, 1, "0.34" }, + { "k", "Singh's formulae parameter", "<value>", 0, 1, "0.06" }, { "verbose", "Enable verbose mode (mute, time, low, medium, full)", "<mode>", scribo::debug::check_verbose_mode, 1, "mute" }, - { "win-size", "Window size", "<size>", 0, 1, "101" }, + { "win-size", "Window size", "<size>", 0, 1, "15" }, {0, 0, 0, 0, 0, 0} }; @@ -98,7 +97,7 @@ int main(int argc, char *argv[]) image2d<value::int_u8> input_1_gl = data::transform(input, mln::fun::v2v::rgb_to_luma<value::int_u8>()); - image2d<bool> out = scribo::binarization::wolf(input_1_gl, w, k); + image2d<bool> out = scribo::binarization::singh(input_1_gl, w, k); io::pbm::save(out, options.arg("output.pbm")); -- 1.7.2.5
participants (1)
-
Guillaume Lazzara