cleanup-2008 1972: Handle fwd iterations on p_array.
https://svn.lrde.epita.fr/svn/oln/branches/cleanup-2008/milena Index: ChangeLog from Thierry Geraud <thierry.geraud@lrde.epita.fr> Handle fwd iterations on p_array. * tests/core/p_array.cc: Add iteration test. * mln/core/internal/site_iterator_base.hh: New; based upon... * mln/core/internal/pseudo_site_base.hh: ...this. * mln/core/internal/pseudo_site_base.hh (subject, q_subject): New; factor those definitions. * mln/core/p_array_piter.hh (p_array_fwd_piter_): Update. (p_array_bkd_piter_): Deactivate. * mln/core/p_array.hh (p_array): Change into constant proxy; move defs into guards. (to_site): Delete mutable version. (change_target): New. * mln/core/concept/site_iterator.hh (operator site): Remove; that was obsolete code. mln/core/concept/site_iterator.hh | 20 - mln/core/internal/pseudo_site_base.hh | 6 mln/core/internal/site_iterator_base.hh | 50 +++- mln/core/p_array.hh | 131 +++++++---- mln/core/p_array_piter.hh | 366 +++++++++++++++----------------- tests/core/p_array.cc | 8 6 files changed, 309 insertions(+), 272 deletions(-) Index: tests/core/p_array.cc --- tests/core/p_array.cc (revision 1971) +++ tests/core/p_array.cc (working copy) @@ -59,7 +59,15 @@ << point2d(p) << ' ' << std::endl; + std::copy(pa.vect().begin(), pa.vect().end(), std::ostream_iterator<point2d>(std::cout, " ")); std::cout << std::endl; + + { + mln_piter_(Arr) p(pa); + for_all(p) + std::cout << p << ' '; + std::cout << std::endl; + } } Index: mln/core/internal/site_iterator_base.hh --- mln/core/internal/site_iterator_base.hh (revision 1971) +++ mln/core/internal/site_iterator_base.hh (working copy) @@ -25,15 +25,15 @@ // reasons why the executable file might be covered by the GNU General // Public License. -#ifndef MLN_CORE_INTERNAL_PSEUDO_SITE_BASE_HH -# define MLN_CORE_INTERNAL_PSEUDO_SITE_BASE_HH +#ifndef MLN_CORE_INTERNAL_SITE_ITERATOR_BASE_HH +# define MLN_CORE_INTERNAL_SITE_ITERATOR_BASE_HH -/*! \file mln/core/internal/pseudo_site_base.hh +/*! \file mln/core/internal/site_iterator_base.hh * - * \brief Base class to factor code for pseudo site classes. + * \brief Base class to factor code for site iterator classes. */ -# include <mln/core/concept/pseudo_site.hh> +# include <mln/core/concept/site_iterator.hh> namespace mln @@ -42,16 +42,16 @@ namespace internal { - /*! \internal A base class for pseudo sites. + /*! \internal A base class for site iterators. * * Parameter \c P is FIXME: a point site type. */ - template <bool is_mutable, typename P, typename E> - struct pseudo_site_base_ : Pseudo_Site<E>, + template <typename P, typename E> + struct site_iterator_base_ : Site_Iterator<E>, proxy_impl<P, E>, - site_impl< is_mutable, + site_impl< false, // Constant access to site / subject. typename site_from<P>::ret, E > { @@ -59,17 +59,41 @@ // The associated site type. typedef typename internal::site_from<P>::ret site; + // The associated subject type (as a Proxy). + typedef P subject; + + // The associated q_subject type (as a Proxy). + typedef const P& q_subject; + + /*! \brief Conversion towards the site it designates. + * + * \warning This is a final method; iterator classes should not + * re-defined this method. + * + * \pre The iterator is valid. + */ + operator site() const; + protected: - pseudo_site_base_(); + site_iterator_base_(); }; #ifndef MLN_INCLUDE_ONLY - template <bool is_mutable, typename P, typename E> + template <typename P, typename E> + inline + site_iterator_base_<P, E>::site_iterator_base_() + { + } + + template <typename P, typename E> inline - pseudo_site_base_<is_mutable, P, E>::pseudo_site_base_() + site_iterator_base_<P, E>::operator site() const { + typedef proxy_impl<P, E> super; + mln_precondition(exact(this)->is_valid()); + return this->super::operator site(); } #endif // ! MLN_INCLUDE_ONLY @@ -79,4 +103,4 @@ } // end of namespace mln -#endif // ! MLN_CORE_INTERNAL_PSEUDO_SITE_BASE_HH +#endif // ! MLN_CORE_INTERNAL_SITE_ITERATOR_BASE_HH Index: mln/core/internal/pseudo_site_base.hh --- mln/core/internal/pseudo_site_base.hh (revision 1971) +++ mln/core/internal/pseudo_site_base.hh (working copy) @@ -59,6 +59,12 @@ // The associated site type. typedef typename internal::site_from<P>::ret site; + // The associated subject type (as a Proxy). + typedef P subject; + + // The associated q_subject type (as a Proxy). + typedef const P& q_subject; + protected: pseudo_site_base_(); }; Index: mln/core/p_array_piter.hh --- mln/core/p_array_piter.hh (revision 1971) +++ mln/core/p_array_piter.hh (working copy) @@ -32,6 +32,7 @@ /// \brief Definition of point iterators on mln::p_array. # include <mln/core/p_array.hh> +# include <mln/core/internal/site_iterator_base.hh> namespace mln @@ -39,32 +40,24 @@ /// \brief Forward iterator on points of a p_array<P>. template <typename P> - struct p_array_fwd_piter_ - : public internal::point_iterator_base_< P, p_array_fwd_piter_<P> > + class p_array_fwd_piter_ + : + public internal::site_iterator_base_< p_array_psite<P>, + p_array_fwd_piter_<P> > { - typedef p_array_fwd_piter_<P> self_; - typedef internal::point_iterator_base_< P, self_ > super_; - public: - /// The associated psite type. - typedef P psite; - - /// The associated point type. - typedef mln_point(P) point; - - enum { dim = super_::dim }; + typedef p_array_fwd_piter_<P> self; + typedef internal::site_iterator_base_<p_array_psite<P>, self> super; - /// Coordinate associated type. - template <typename S> - p_array_fwd_piter_(const Site_Set<S>& s); + public: - /// Reference of the corresponding psite. - const psite& to_psite() const; + /// Constructor with no argument. + p_array_fwd_piter_(); - /// Reference of the corresponding point. - const point& to_point() const; + /// Constructor. + p_array_fwd_piter_(const p_array<P>& arr); - /// Read-only access to the \p i-th coordinate. - mln_coord(point) operator[](unsigned i) const; + /// Change of site set target. + void change_target(const p_array<P>& arr); /// Test if the iterator is valid. bool is_valid() const; @@ -78,73 +71,75 @@ /// Go to the next point. void next_(); - /// Convert the iterator into a psite. - operator psite() const; - - protected: - const std::vector<P>& vect_; - // FIXME: Why it's unsigned in fwd iterator and signed in the bkd one ? - unsigned i_; - psite p_; - }; - - - - /// \brief Backward iterator on points of a p_array<P>. - template <typename P> - struct p_array_bkd_piter_ - : public internal::point_iterator_base_< P, p_array_bkd_piter_<P> > - { - typedef p_array_bkd_piter_<P> self_; - typedef internal::point_iterator_base_< P, self_ > super_; - public: - /// The associated psite type. - typedef P psite; - - /// The associated point type. - typedef mln_point(P) point; - - enum { dim = super_::dim }; - - /// Coordinate associated type. - template <typename S> - p_array_bkd_piter_(const Site_Set<S>& s); - - /// Reference of the corresponding psite. - const psite& to_psite() const; - - /// Reference of the corresponding point. - const point& to_point() const; + /// Return the subject. + const p_array_psite<P>& unproxy() const; - /// Read-only access to the \p i-th coordinate. - mln_coord(point) operator[](unsigned i) const; + // As a Site_Proxy: + typedef typename super::site site; + const site& to_site() const; - /// Test if the iterator is valid. - bool is_valid() const; - - /// Invalidate the iterator. - void invalidate(); + protected: - /// Start an iteration. - void start(); + p_array_psite<P> p_; + }; - /// Go to the next point. - void next_(); - /// Convert the iterator into a psite. - operator psite() const; - protected: - const std::vector<P>& vect_; - /* FIXME: See the comment on p_array_fwd_piter_<P>::i_ above. We - could turn this `int' into an `unsigned'. Then, - - setting the value of i_ to -1 (== UINT_MAX) in invalidate(), - - and having valid() test whether i_ is strictly smaller than - vect_.size() - should work in both iterators (fwd and bkd). */ - int i_; - psite p_; - }; +// /// \brief Backward iterator on points of a p_array<P>. +// template <typename P> +// struct p_array_bkd_piter_ +// : public internal::point_iterator_base_< P, p_array_bkd_piter_<P> > +// { +// typedef p_array_bkd_piter_<P> self_; +// typedef internal::point_iterator_base_< P, self_ > super_; +// public: +// /// The associated psite type. +// typedef P psite; + +// /// The associated point type. +// typedef mln_point(P) point; + +// enum { dim = super_::dim }; + +// /// Coordinate associated type. +// template <typename S> +// p_array_bkd_piter_(const Site_Set<S>& s); + +// /// Reference of the corresponding psite. +// const psite& to_psite() const; + +// /// Reference of the corresponding point. +// const point& to_point() const; + +// /// Read-only access to the \p i-th coordinate. +// mln_coord(point) operator[](unsigned i) const; + +// /// Test if the iterator is valid. +// bool is_valid() const; + +// /// Invalidate the iterator. +// void invalidate(); + +// /// Start an iteration. +// void start(); + +// /// Go to the next point. +// void next_(); + +// /// Convert the iterator into a psite. +// operator psite() const; + +// protected: +// const std::vector<P>& vect_; +// /* FIXME: See the comment on p_array_fwd_piter_<P>::i_ above. We +// could turn this `int' into an `unsigned'. Then, +// - setting the value of i_ to -1 (== UINT_MAX) in invalidate(), +// - and having valid() test whether i_ is strictly smaller than +// vect_.size() +// should work in both iterators (fwd and bkd). */ +// int i_; +// psite p_; +// }; @@ -155,38 +150,25 @@ `------------------------*/ template <typename P> - template <typename S> inline - p_array_fwd_piter_<P>::p_array_fwd_piter_(const Site_Set<S>& s) - : vect_(exact(s).vect()) + p_array_fwd_piter_<P>::p_array_fwd_piter_() { - invalidate(); } template <typename P> inline - const P& - p_array_fwd_piter_<P>::to_psite() const + p_array_fwd_piter_<P>::p_array_fwd_piter_(const p_array<P>& arr) { - return p_; + change_target(arr); } template <typename P> inline - const mln_point(P)& - p_array_fwd_piter_<P>::to_point() const - { - return p_.to_point(); - } - - template <typename P> - inline - mln_coord(mln_point_(P)) - p_array_fwd_piter_<P>::operator[](unsigned i) const + void + p_array_fwd_piter_<P>::change_target(const p_array<P>& arr) { - mln_precondition(i < dim); - mln_precondition(is_valid()); - return p_.to_point()[i]; + p_.change_target(arr); + invalidate(); } template <typename P> @@ -194,7 +176,7 @@ bool p_array_fwd_piter_<P>::is_valid() const { - return i_ < vect_.size(); + return p_.target() != 0 && p_.index() < int(p_.target()->nsites()); } template <typename P> @@ -202,7 +184,8 @@ void p_array_fwd_piter_<P>::invalidate() { - i_ = vect_.size(); + if (p_.target() != 0) + p_.index() = p_.target()->nsites(); } template <typename P> @@ -210,9 +193,8 @@ void p_array_fwd_piter_<P>::start() { - i_ = 0; - if (is_valid()) - p_ = vect_[i_]; + mln_precondition(p_.target() != 0); + p_.index() = 0; } template <typename P> @@ -220,102 +202,108 @@ void p_array_fwd_piter_<P>::next_() { - ++i_; - if (is_valid()) - p_ = vect_[i_]; + ++p_.index(); } template <typename P> inline - p_array_fwd_piter_<P>::operator P() const + const p_array_psite<P>& + p_array_fwd_piter_<P>::unproxy() const { - mln_precondition(is_valid()); return p_; } - - /*------------------------. - | p_array_bkd_piter_<P>. | - `------------------------*/ - template <typename P> - template <typename S> inline - p_array_bkd_piter_<P>::p_array_bkd_piter_(const Site_Set<S>& s) - : vect_(exact(s).vect()) + const typename p_array_fwd_piter_<P>::site& + p_array_fwd_piter_<P>::to_site() const { - invalidate(); + mln_precondition(p_.target() != 0); + return p_.to_site(); } - template <typename P> - inline - const P& - p_array_bkd_piter_<P>::to_psite() const - { - return p_; - } - - template <typename P> - inline - const mln_point(P)& - p_array_bkd_piter_<P>::to_point() const - { - return p_.to_point(); - } - - template <typename P> - inline - mln_coord(mln_point_(P)) - p_array_bkd_piter_<P>::operator[](unsigned i) const - { - mln_precondition(i < dim); - mln_precondition(is_valid()); - return p_.to_point()[i]; - } - - template <typename P> - inline - bool - p_array_bkd_piter_<P>::is_valid() const - { - return i_ >= 0; - } - - template <typename P> - inline - void - p_array_bkd_piter_<P>::invalidate() - { - i_ = -1; - } - - template <typename P> - inline - void - p_array_bkd_piter_<P>::start() - { - i_ = vect_.size() - 1; - if (is_valid()) - p_ = vect_[i_]; - } - - template <typename P> - inline - void - p_array_bkd_piter_<P>::next_() - { - --i_; - if (is_valid()) - p_ = vect_[i_]; - } + /*------------------------. + | p_array_bkd_piter_<P>. | + `------------------------*/ - template <typename P> - inline - p_array_bkd_piter_<P>::operator P() const - { - mln_precondition(is_valid()); - return p_; - } +// template <typename P> +// template <typename S> +// inline +// p_array_bkd_piter_<P>::p_array_bkd_piter_(const Site_Set<S>& s) +// : vect_(exact(s).vect()) +// { +// invalidate(); +// } + +// template <typename P> +// inline +// const P& +// p_array_bkd_piter_<P>::to_psite() const +// { +// return p_; +// } + +// template <typename P> +// inline +// const mln_point(P)& +// p_array_bkd_piter_<P>::to_point() const +// { +// return p_.to_point(); +// } + +// template <typename P> +// inline +// mln_coord(mln_point_(P)) +// p_array_bkd_piter_<P>::operator[](unsigned i) const +// { +// mln_precondition(i < dim); +// mln_precondition(is_valid()); +// return p_.to_point()[i]; +// } + +// template <typename P> +// inline +// bool +// p_array_bkd_piter_<P>::is_valid() const +// { +// return i_ >= 0; +// } + +// template <typename P> +// inline +// void +// p_array_bkd_piter_<P>::invalidate() +// { +// i_ = -1; +// } + +// template <typename P> +// inline +// void +// p_array_bkd_piter_<P>::start() +// { +// i_ = vect_.size() - 1; +// if (is_valid()) +// p_ = vect_[i_]; +// } + +// template <typename P> +// inline +// void +// p_array_bkd_piter_<P>::next_() +// { +// --i_; +// if (is_valid()) +// p_ = vect_[i_]; +// } + +// template <typename P> +// inline +// p_array_bkd_piter_<P>::operator P() const +// { +// mln_precondition(is_valid()); +// return p_; +// } # endif // ! MLN_INCLUDE_ONLY Index: mln/core/p_array.hh --- mln/core/p_array.hh (revision 1971) +++ mln/core/p_array.hh (working copy) @@ -49,10 +49,10 @@ template <typename P> struct p_array_bkd_piter_; - // HOT... + // p_array_psite<P> template <typename P> - class p_array_psite : public internal::pseudo_site_base_< true, // Mutable. + class p_array_psite : public internal::pseudo_site_base_< false, // Not mutable. P, p_array_psite<P> > { @@ -63,59 +63,33 @@ // As a Proxy: - typedef P subject; - typedef const P& q_subject; - q_subject unproxy() const; - P& unproxy(); + const P& unproxy() const; // As a Site_Proxy: typedef typename super::site site; - const site& to_site() const - { - const site* s; - internal::get_adr(s, *this); - return *s; - } - - site& to_site() - { - site* s; - internal::get_adr(s, *this); - return *s; - } + const site& to_site() const; // As Itself. - p_array_psite() - : arr_(0), - i_(0) - { - } + p_array_psite(); - p_array_psite(p_array<P>& arr, unsigned i) - : arr_(&arr), - i_(int(i)) - { - } + p_array_psite(const p_array<P>& arr, int i); - int index() const - { - return i_; - } + int index() const; - const p_array<P>* target() const - { - return arr_; - } + int& index(); - void print() const - { - std::cout << i_ << "-th site of " << arr_ << " => site " << to_site() << std::endl; - } + const p_array<P>* target() const; - p_array<P>* arr_; // FIXME: Or const! + void change_target(const p_array<P>& arr); + + void print() const; + + private: + + const p_array<P>* arr_; int i_; }; @@ -159,7 +133,7 @@ typedef p_array_fwd_piter_<P> fwd_piter; /// Backward Point_Iterator associated type. - typedef p_array_bkd_piter_<P> bkd_piter; + typedef p_array_fwd_piter_<P> bkd_piter; // HOT: FIXME /// Constructor. p_array(); @@ -235,7 +209,7 @@ p_array<P>::has(const psite& p) const { mln_precondition(p.target() == this); // FIXME: Refine. - if (p.index() < 0 || p.index() >= vect_.size()) + if (p.index() < 0 || p.index() >= int(vect_.size())) return false; site s_ = (*this)[p.index()]; mln_invariant(p.to_site() == s_); @@ -308,17 +282,74 @@ template <typename P> inline - const P& - p_array_psite<P>::unproxy() const + p_array_psite<P>::p_array_psite() + : arr_(0), + i_(0) { - mln_precondition(arr_ != 0); - return (*arr_)[i_]; } template <typename P> inline - P& - p_array_psite<P>::unproxy() + p_array_psite<P>::p_array_psite(const p_array<P>& arr, int i) + : arr_(&arr), + i_(i) + { + } + + template <typename P> + inline + const typename p_array_psite<P>::site& + p_array_psite<P>::to_site() const + { + const site* s; + internal::get_adr(s, *this); + return *s; + } + + template <typename P> + inline + int + p_array_psite<P>::index() const + { + return i_; + } + + template <typename P> + inline + int& + p_array_psite<P>::index() + { + return i_; + } + + template <typename P> + inline + const p_array<P>* + p_array_psite<P>::target() const + { + return arr_; + } + + template <typename P> + inline + void + p_array_psite<P>::change_target(const p_array<P>& arr) + { + arr_ = & arr; + } + + template <typename P> + inline + void + p_array_psite<P>::print() const + { + std::cout << i_ << "-th site of " << arr_ << " => site " << to_site() << std::endl; + } + + template <typename P> + inline + const P& + p_array_psite<P>::unproxy() const { mln_precondition(arr_ != 0); return (*arr_)[i_]; Index: mln/core/concept/site_iterator.hh --- mln/core/concept/site_iterator.hh (revision 1971) +++ mln/core/concept/site_iterator.hh (working copy) @@ -71,18 +71,6 @@ */ void next(); // final - using Site_Proxy<E>::site; - - /*! \brief Go to the next element. - * - * \warning This is a final method; iterator classes should not - * re-defined this method. The actual "next" operation has to be - * defined through the \em next_ method. - * - * \pre The iterator is valid. - */ - operator site() const; - protected: Site_Iterator(); }; @@ -101,14 +89,6 @@ template <typename E> inline - Site_Iterator<E>::operator site() const - { - mln_precondition(exact(this)->is_valid()); - return exact(this)->to_site(); - } - - template <typename E> - inline Site_Iterator<E>::Site_Iterator() { bool (E::*m1)() const = & E::is_valid;
participants (1)
-
Thierry Geraud