1036: Make value::set works for any type.

https://svn.lrde.epita.fr/svn/oln/trunk/milena Index: ChangeLog from Thierry Geraud <thierry.geraud@lrde.epita.fr> Make value::set works for any type. * mln/value/set.hh: Rename as... * mln/value/internal/iterable_set.hh: ...this. (the): Remove. (E): New. * mln/value/set.hh: New. * tests/vset.cc, * tests/histo.cc, * TODO, * mln/core/macros.hh, * mln/core/trait/is_lowq.hh, * mln/core/fimage.hh, * mln/core/image2d_b.hh, * mln/level/naive/median.hh, * mln/level/was.median.hh, * mln/level/fast_median.hh, * mln/level/transform.hh, * mln/level/median.hh, * mln/accu/histo.hh, * mln/accu/median.hh, * mln/accu/median_alt.hh, * mln/value/props.hh, * mln/value/cast.hh, * mln/value/int_u.hh: Update. TODO | 2 mln/accu/histo.hh | 68 +++++++++------------------ mln/accu/median.hh | 47 ++++--------------- mln/accu/median_alt.hh | 4 - mln/core/fimage.hh | 4 - mln/core/image2d_b.hh | 2 mln/core/macros.hh | 5 +- mln/core/trait/is_lowq.hh | 6 +- mln/level/fast_median.hh | 2 mln/level/median.hh | 5 +- mln/level/naive/median.hh | 2 mln/level/transform.hh | 2 mln/level/was.median.hh | 4 - mln/value/cast.hh | 6 +- mln/value/int_u.hh | 8 --- mln/value/internal/iterable_set.hh | 57 ++++++++++------------- mln/value/props.hh | 13 +---- mln/value/set.hh | 91 +++++++++++-------------------------- tests/histo.cc | 22 +------- tests/vset.cc | 32 ++++++------- 20 files changed, 138 insertions(+), 244 deletions(-) Index: tests/vset.cc --- tests/vset.cc (revision 1035) +++ tests/vset.cc (working copy) @@ -35,29 +35,31 @@ -int main() +template <typename T> +void test() { - using namespace mln; - - typedef bool T; - // typedef value::int_u8 T; - // typedef short T; - - typedef value::set_<T> S; + typedef mln::value::set<T> S; S s; - { - S::fwd_viter v(s); + mln_fwd_viter(S) v(s); for_all(v) std::cout << v << ' '; std::cout << std::endl; - } - { - S::bkd_viter v(s); - for_all(v) - std::cout << v << ' '; + mln_bkd_viter(S) w(s); + for_all(w) + std::cout << w << ' '; std::cout << std::endl; } + + +int main() +{ + using namespace mln; + + test<bool>(); +// test<unsigned char>(); +// test<unsigned short>(); +// test<value::int_u8>(); } Index: tests/histo.cc --- tests/histo.cc (revision 1035) +++ tests/histo.cc (working copy) @@ -30,7 +30,6 @@ * \brief Tests on mln::value::histo<S>. */ -#include <mln/value/int_u.hh> #include <mln/accu/histo.hh> @@ -38,11 +37,8 @@ int main() { using namespace mln; - using namespace mln::value; - using namespace mln::accu; - - histo_on_type<bool> h; + accu::histo< value::set<bool> > h; for (unsigned i = 0; i < 5; ++i) h.take(false); @@ -50,18 +46,6 @@ h.take(true); h.untake(true); - std::cout << h << std::endl; - std::cout << h[0] * 10 + h[1] << std::endl; - std::cout << h(false) * 10 + h(true) << std::endl; - - h.init(); - std::cout << h << std::endl; - - - // ... - - - typedef value::set_<int_u8> S; - histo_on_set<S> h_u8(S::the()); - std::cout << h_u8 << std::endl; + mln_assertion(h[0] * 10 + h[1] = 51); + mln_assertion(h(false) * 10 + h(true) = 51); } Index: TODO --- TODO (revision 1035) +++ TODO (working copy) @@ -18,7 +18,6 @@ value::proxy to dispatch read/write + the corresponding image type a mean_value object { sum; count } and operator+ t_image to "transpose" the 0 and the i-th coordinates -image defined by f/pset ** extensions @@ -35,7 +34,6 @@ * clean-up -accu::histo and median: remove inheritance select_function in fun::internal::selector_p2? etc. Index: mln/core/macros.hh --- mln/core/macros.hh (revision 1035) +++ mln/core/macros.hh (working copy) @@ -149,7 +149,10 @@ # define mln_value(T) typename T::value /// Shortcut to the kind of values for an image with type \c I. -# define mln_value_kind(T) typename mln::value::props< mln_value(I) >::kind +# define mln_value_kind(I) typename mln::value::props< mln_value(I) >::kind + +/// Shortcut to test if the values of an image with type \c I are lowly quantifized. +# define mln_is_value_lowq(I) typename mln::trait::is_lowq< mln_value(I) >::ret /// Shortcut to access the type of value set (vset) associated to T. # define mln_vset(T) typename T::vset Index: mln/core/trait/is_lowq.hh --- mln/core/trait/is_lowq.hh (revision 1035) +++ mln/core/trait/is_lowq.hh (working copy) @@ -37,7 +37,7 @@ # include <mln/value/props.hh> -# define mln_is_lowq(I) typename mln::trait::is_lowq< I >::ret +# define mln_is_lowq(T) typename mln::trait::is_lowq< T >::ret @@ -50,10 +50,10 @@ // FIXME: Doc! - template <typename I> + template <typename T> struct is_lowq { - typedef typename metal::bool_<( mln_card(mln_value(I)) != 0 )>::type ret; + typedef typename metal::bool_<( mln_card(T) != 0 )>::type ret; }; Index: mln/core/fimage.hh --- mln/core/fimage.hh (revision 1035) +++ mln/core/fimage.hh (working copy) @@ -63,7 +63,7 @@ typedef void lvalue; // FIXME /// Value set associated type. - typedef mln::value::set_<mln_result(F)> vset; + typedef mln::value::set<mln_result(F)> vset; /// Constructor. @@ -156,7 +156,7 @@ } template <typename F, typename S> - const mln::value::set_<mln_result(F)>& + const mln::value::set<mln_result(F)>& fimage<F,S>::values() const { return vset::the(); Index: mln/core/image2d_b.hh --- mln/core/image2d_b.hh (revision 1035) +++ mln/core/image2d_b.hh (working copy) @@ -119,7 +119,7 @@ }; /// Value_Set associated type. - typedef mln::value::set_<T> vset; + typedef mln::value::set<T> vset; /// Constructor without argument. Index: mln/level/naive/median.hh --- mln/level/naive/median.hh (revision 1035) +++ mln/level/naive/median.hh (working copy) @@ -78,7 +78,7 @@ { mln_piter(I) p(input.domain()); mln_qiter(W) q(win, p); - accu::median_on<mln_value(I)> med; + accu::median<mln_vset(I)> med(input.values()); for_all(p) { Index: mln/level/was.median.hh --- mln/level/was.median.hh (revision 1035) +++ mln/level/was.median.hh (working copy) @@ -72,7 +72,7 @@ q_bp(win_bkd_plus, p), q_bm(win_bkd_minus, p), q_top(win_top, p), q_bot(win_bot, p); - accu::median_on<mln_value(I)> med; + accu::median<mln_vset(I)> med(input.values()); // initialization @@ -146,7 +146,7 @@ int& row = p.row(); int& col = p.col(); - accu::median_on<mln_value(I)> med; + accu::median<mln_vset(I)> med(input.values()); for (row = input.min_row(); row <= max_row; ++row) { Index: mln/level/fast_median.hh --- mln/level/fast_median.hh (revision 1035) +++ mln/level/fast_median.hh (working copy) @@ -84,7 +84,7 @@ win_bot = win - (win + up), win_top = (win + up) - win; - accu::median_on<mln_value(I)> med; + accu::median<mln_vset(I)> med(input.values()); // initialization Index: mln/level/transform.hh --- mln/level/transform.hh (revision 1035) +++ mln/level/transform.hh (working copy) @@ -120,7 +120,7 @@ void transform(const Image<I>& input, const Function_v2v<F>& f, Image<O>& output) { mln_precondition(exact(output).domain() >= exact(input).domain()); - impl::transform(mln_is_lowq(I)(), + impl::transform(mln_is_value_lowq(I)(), exact(input), exact(f), exact(output)); } Index: mln/level/median.hh --- mln/level/median.hh (revision 1035) +++ mln/level/median.hh (working copy) @@ -80,10 +80,10 @@ // aux data + accu::median<mln_vset(I)> med; mln_point(I) p; window2d win_fp, win_fm, win_bp, win_bm, win_dp, win_dm; mln_qiter(W) q_fp, q_fm, q_bp, q_bm, q_dp, q_dm; - accu::median_on<mln_value(I)> med; // ctor @@ -94,6 +94,7 @@ win(exact(win_)), output(exact(output_)), // aux data + med(input.values()), p(), win_fp(win - (win + left)), win_fm((win + left) - win), win_bp(win - (win + right)), win_bm((win + right) - win), @@ -171,7 +172,7 @@ coord& row = p.row(); coord& col = p.col(); - accu::median_on<mln_value(I)> med; + accu::median<mln_vset(I)> med(input.values()); for (row = input.min_row(); row <= max_row; ++row) { Index: mln/accu/histo.hh --- mln/accu/histo.hh (revision 1035) +++ mln/accu/histo.hh (working copy) @@ -51,9 +51,10 @@ /*! Generic histogram class over a value set with type \c S. */ template <typename S> - struct histo_on_set : public Accumulator< histo_on_set<S> > + struct histo : public Accumulator< histo<S> > { - histo_on_set(const Value_Set<S>& s); + histo(const Value_Set<S>& s); + histo(); typedef mln_value(S) value; @@ -79,41 +80,32 @@ template <typename S> - std::ostream& operator<<(std::ostream& ostr, const histo_on_set<S>& h); - - - - - /*! Generic histogram class over the set of values of type \c T. - * - * \todo Inheritance is badly formed since this concrete class - * derives from another concrete class. - */ - template <typename T> - struct histo_on_type : public histo_on_set< value::set_<T> > - { - histo_on_type(); - }; + std::ostream& operator<<(std::ostream& ostr, const histo<S>& h); # ifndef MLN_INCLUDE_ONLY - - // histo_on_set<S> - template <typename S> - histo_on_set<S>::histo_on_set(const Value_Set<S>& s) + histo<S>::histo(const Value_Set<S>& s) : s_(exact(s)), - h_(exact(s).nvalues(), 0), + h_(s_.nvalues(), 0), + sum_(0) + { + } + + template <typename S> + histo<S>::histo() + : s_(S::the()), + h_(s_.nvalues(), 0), sum_(0) { } template <typename S> void - histo_on_set<S>::take(const value& v) + histo<S>::take(const value& v) { ++h_[s_.index_of(v)]; ++sum_; @@ -121,7 +113,7 @@ template <typename S> void - histo_on_set<S>::untake(const value& v) + histo<S>::untake(const value& v) { mln_precondition(h_[s_.index_of(v)] > 0); mln_precondition(sum_ > 0); @@ -131,7 +123,7 @@ template <typename S> void - histo_on_set<S>::init() + histo<S>::init() { std::fill(h_.begin(), h_.end(), 0); sum_ = 0; @@ -139,14 +131,14 @@ template <typename S> std::size_t - histo_on_set<S>::operator()(const value& v) const + histo<S>::operator()(const value& v) const { return h_[s_.index_of(v)]; } template <typename S> std::size_t - histo_on_set<S>::operator[](std::size_t i) const + histo<S>::operator[](std::size_t i) const { mln_precondition(i < s_.nvalues()); return h_[i]; @@ -154,54 +146,42 @@ template <typename S> std::size_t - histo_on_set<S>::nvalues() const + histo<S>::nvalues() const { return s_.nvalues(); } template <typename S> std::size_t - histo_on_set<S>::sum() const + histo<S>::sum() const { return sum_; } template <typename S> const std::vector<std::size_t>& - histo_on_set<S>::vec() const + histo<S>::vec() const { return h_; } template <typename S> const S& - histo_on_set<S>::vset() const + histo<S>::vset() const { return s_; } template <typename S> - std::ostream& operator<<(std::ostream& ostr, const histo_on_set<S>& h) + std::ostream& operator<<(std::ostream& ostr, const histo<S>& h) { mln_viter(S) v(h.vset()); for_all(v) if (h(v) != 0) ostr << v << ':' << h(v) << ' '; - ostr << std::endl; return ostr; } - - // histo_on_type<T> - - template <typename T> - histo_on_type<T>::histo_on_type() - : histo_on_set< value::set_<T> >(value::set_<T>::the()) - { - } - - - # endif // ! MLN_INCLUDE_ONLY } // end of namespace mln::accu Index: mln/accu/median.hh --- mln/accu/median.hh (revision 1035) +++ mln/accu/median.hh (working copy) @@ -53,6 +53,7 @@ typedef mln_value(S) value; median(const Value_Set<S>& s); + median(); void take(const value& v); void untake(const value& v); @@ -63,20 +64,11 @@ operator mln_value(S) () const; value to_value() const; - const histo_on_set<S>& histo() const; - - // FIXME: remove - void debug__() const - { - std::cout << " i = " << i_ - << " v = " << v_ - << " s = " << sum_minus_ << " ; " << h_[i_] << " ; " << sum_plus_ << " = " << h_.sum() - << std::endl; - } + const accu::histo<S>& histo() const; protected: - mutable histo_on_set<S> h_; + mutable accu::histo<S> h_; const S& s_; // derived from h_ mutable std::size_t sum_minus_, sum_plus_; @@ -92,24 +84,8 @@ }; - /*! Generic median class over the set of values of type \c T. - * - * \todo Inheritance is badly formed since this concrete class - * derives from another concrete class. - */ - template <typename T> - struct median_on : public median< value::set_<T> > - { - median_on() - : median< value::set_<T> >(value::set_<T>::the()) - { - } - }; - - # ifndef MLN_INCLUDE_ONLY - template <typename S> median<S>::median(const Value_Set<S>& s) : h_(s), @@ -118,6 +94,13 @@ init(); } + template <typename S> + median<S>::median() + : h_(), + s_(h_.vset()) + { + init(); + } template <typename S> void @@ -134,7 +117,6 @@ valid_ = false; } - template <typename S> void median<S>::untake(const value& v) @@ -151,7 +133,6 @@ valid_ = false; } - template <typename S> void median<S>::update_() const @@ -177,7 +158,6 @@ } } - template <typename S> void median<S>::go_minus_() const @@ -194,7 +174,6 @@ v_ = s_[i_]; } - template <typename S> void median<S>::go_plus_() const @@ -211,7 +190,6 @@ v_ = s_[i_]; } - template <typename S> void median<S>::init() @@ -224,7 +202,6 @@ valid_ = true; } - template <typename S> median<S>::operator mln_value(S) () const { @@ -241,7 +218,7 @@ } template <typename S> - const histo_on_set<S>& + const accu::histo<S>& median<S>::histo() const { return h_; @@ -250,11 +227,9 @@ template <typename S> std::ostream& operator<<(std::ostream& ostr, const median<S>& m) { - m.debug__(); return ostr << m.to_value(); } - # endif // ! MLN_INCLUDE_ONLY } // end of namespace mln::accu Index: mln/accu/median_alt.hh --- mln/accu/median_alt.hh (revision 1035) +++ mln/accu/median_alt.hh (working copy) @@ -86,10 +86,10 @@ template <typename T> - struct median_alt_on : public median_alt< value::set_<T> > + struct median_alt_on : public median_alt< value::set<T> > { median_alt_on() - : median_alt< value::set_<T> >(value::set_<T>::the()) + : median_alt< value::set<T> >(value::set<T>::the()) { } }; Index: mln/value/props.hh --- mln/value/props.hh (revision 1035) +++ mln/value/props.hh (working copy) @@ -65,19 +65,14 @@ { - /*! Class that defines the properties of the value type \c T. + /*! Class that defines the properties (by default) of any value + * type \c T. */ template <typename T> struct props { - /// Minimum value for type \c T. - static const T min; - - /// Maximum value for type \c T. - static const T max; - - /// Number of values for type \c T. - static const std::size_t card; + typedef data_kind kind; + static const std::size_t card = 0; }; Index: mln/value/cast.hh --- mln/value/cast.hh (revision 1035) +++ mln/value/cast.hh (working copy) @@ -47,7 +47,7 @@ * */ template <typename T, typename I> - struct cast_image : public internal::image_base_< mln_pset(I), cast_image<T,I> > + struct cast_image : public mln::internal::image_base_< mln_pset(I), cast_image<T,I> > { /// Point_Site associated type. typedef mln_psite(I) psite; @@ -65,7 +65,7 @@ typedef void lvalue; // FIXME /// Value set associated type. - typedef mln::value::set_<T> vset; + typedef mln::value::set<T> vset; /// Constructor. @@ -159,7 +159,7 @@ } template <typename T, typename I> - const mln::value::set_<T>& + const mln::value::set<T>& cast_image<T,I>::values() const { return vset::the(); Index: mln/value/set.hh --- mln/value/set.hh (revision 1035) +++ mln/value/set.hh (working copy) @@ -33,8 +33,8 @@ * \brief Define some basic sets of values from value types. */ -# include <mln/core/concept/value_set.hh> -# include <mln/value/props.hh> +# include <mln/value/internal/iterable_set.hh> +# include <mln/core/trait/is_lowq.hh> namespace mln @@ -43,41 +43,41 @@ namespace value { - // Fwd decls. - template <typename S> struct fwd_viter_; - template <typename S> struct bkd_viter_; + // Fwd decl. + template <typename T> struct set; - /*! Class that defines the set of values of type \c T. - * - * This is an exhaustive value set over \c T. - */ - template <typename T> - struct set_ : public Value_Set< set_<T> > + + namespace internal { - /// Value associated type. - typedef T value; - /// Forward Value_Iterator associated type. - typedef fwd_viter_< set_<T> > fwd_viter; + template <typename T, typename lowq = metal::false_ > + struct run_set_selector_ // no inheritance + {}; - /// Backward Value_Iterator associated type. - typedef bkd_viter_< set_<T> > bkd_viter; + template <typename T> + struct run_set_selector_< T, metal::true_ > // lowq so iterable + : + public iterable_set< T, mln::value::set<T> > + {}; - /// Test if \p v belongs to this set: always true! - bool has(const T& v) const; + template <typename T> + struct set_selector_ : public run_set_selector_< T, mln_is_lowq(T) > + {}; - /// Give the \p i-th value. - T operator[](std::size_t i) const; + } // end of namespace mln::value::internal - /// Give the index of value \p v in this set. - std::size_t index_of(const T& v) const; - /// Give the number of values. - std::size_t nvalues() const; + /*! Class that defines the set of values of type \c T. + * + * This is the exhaustive set of values obtainable from type \c T. + */ + template <typename T> + struct set : public internal::set_selector_<T> + { /// Return a singleton. - static const set_<T>& the(); + static const set<T>& the(); }; @@ -85,39 +85,10 @@ # ifndef MLN_INCLUDE_ONLY template <typename T> - bool - set_<T>::has(const T&) const - { - return true; - } - - template <typename T> - T - set_<T>::operator[](std::size_t i) const + const set<T>& + set<T>::the() { - mln_precondition(i < nvalues()); - return mln_min(T) + i; - } - - template <typename T> - std::size_t - set_<T>::index_of(const T& v) const - { - return v - mln_min(T); - } - - template <typename T> - std::size_t - set_<T>::nvalues() const - { - return mln_card(T); - } - - template <typename T> - const set_<T>& - set_<T>::the() - { - static set_<T> the_; + static set<T> the_; return the_; } @@ -125,11 +96,7 @@ } // end of namespace mln::value - } // end of namespace mln -# include <mln/value/viter.hh> - - #endif // ! MLN_VALUE_SET_HH Index: mln/value/int_u.hh --- mln/value/int_u.hh (revision 1035) +++ mln/value/int_u.hh (working copy) @@ -33,10 +33,10 @@ * \brief Define a generic class for unsigned integers. */ -# include <mln/core/concept/value.hh> # include <mln/metal/math.hh> # include <mln/value/internal/value_like.hh> # include <mln/value/props.hh> +# include <mln/value/set.hh> namespace mln @@ -89,15 +89,11 @@ }; - // Fwd decl. - template <typename T> struct vset_; - - /// Alias for unsigned 8bit integers. typedef int_u_<8> int_u8; /// Alias for the set of unsigned 8bit integers. - typedef vset_<int_u8> int_u8_set; + typedef set<int_u8> int_u8_set; Index: mln/value/internal/iterable_set.hh --- mln/value/internal/iterable_set.hh (revision 1035) +++ mln/value/internal/iterable_set.hh (working copy) @@ -25,12 +25,12 @@ // reasons why the executable file might be covered by the GNU General // Public License. -#ifndef MLN_VALUE_SET_HH -# define MLN_VALUE_SET_HH +#ifndef MLN_VALUE_INTERNAL_ITERABLE_SET_HH +# define MLN_VALUE_INTERNAL_ITERABLE_SET_HH -/*! \file mln/value/set.hh +/*! \file mln/value/internal/iterable_set.hh * - * \brief Define some basic sets of values from value types. + * \brief Define the iterable value set derived from a type. */ # include <mln/core/concept/value_set.hh> @@ -48,83 +48,76 @@ template <typename S> struct bkd_viter_; + namespace internal + { + /*! Class that defines the set of values of type \c T. * - * This is an exhaustive value set over \c T. + * This is the exhaustive iterable_set of values obtainable from type \c T. */ - template <typename T> - struct set_ : public Value_Set< set_<T> > + template <typename T, typename E> + struct iterable_set : public Value_Set<E> { /// Value associated type. typedef T value; /// Forward Value_Iterator associated type. - typedef fwd_viter_< set_<T> > fwd_viter; + typedef fwd_viter_<E> fwd_viter; /// Backward Value_Iterator associated type. - typedef bkd_viter_< set_<T> > bkd_viter; + typedef bkd_viter_<E> bkd_viter; - /// Test if \p v belongs to this set: always true! + /// Test if \p v belongs to this iterable_set: always true! bool has(const T& v) const; /// Give the \p i-th value. T operator[](std::size_t i) const; - /// Give the index of value \p v in this set. + /// Give the index of value \p v in this iterable_set. std::size_t index_of(const T& v) const; /// Give the number of values. std::size_t nvalues() const; - - /// Return a singleton. - static const set_<T>& the(); }; # ifndef MLN_INCLUDE_ONLY - template <typename T> + template <typename T, typename E> bool - set_<T>::has(const T&) const + iterable_set<T,E>::has(const T&) const { return true; } - template <typename T> + template <typename T, typename E> T - set_<T>::operator[](std::size_t i) const + iterable_set<T,E>::operator[](std::size_t i) const { mln_precondition(i < nvalues()); return mln_min(T) + i; } - template <typename T> + template <typename T, typename E> std::size_t - set_<T>::index_of(const T& v) const + iterable_set<T,E>::index_of(const T& v) const { return v - mln_min(T); } - template <typename T> + template <typename T, typename E> std::size_t - set_<T>::nvalues() const + iterable_set<T,E>::nvalues() const { return mln_card(T); } - template <typename T> - const set_<T>& - set_<T>::the() - { - static set_<T> the_; - return the_; - } - # endif // ! MLN_INCLUDE_ONLY - } // end of namespace mln::value + } // end of namespace mln::value::internal + } // end of namespace mln::value } // end of namespace mln @@ -132,4 +125,4 @@ # include <mln/value/viter.hh> -#endif // ! MLN_VALUE_SET_HH +#endif // ! MLN_VALUE_INTERNAL_ITERABLE_SET_HH
participants (1)
-
Thierry Geraud