2392: Add iterators on n-faces able to convert to mln::any_face_handle's.

* mln/core/complex_faces_iter.hh: New. --- milena/ChangeLog | 6 + milena/mln/core/complex_faces_iter.hh | 262 +++++++++++++++++++++++++++++++++ 2 files changed, 268 insertions(+), 0 deletions(-) create mode 100644 milena/mln/core/complex_faces_iter.hh diff --git a/milena/ChangeLog b/milena/ChangeLog index 72e25d3..e82e082 100644 --- a/milena/ChangeLog +++ b/milena/ChangeLog @@ -41,6 +41,12 @@ 2008-09-24 Roland Levillain <roland@lrde.epita.fr> + Add iterators on n-faces able to convert to mln::any_face_handle's. + + * mln/core/complex_faces_iter.hh: New. + +2008-09-24 Roland Levillain <roland@lrde.epita.fr> + Simplify iterators on complexes. * mln/core/complex_iter.hh, mln/core/faces_iter.hh: diff --git a/milena/mln/core/complex_faces_iter.hh b/milena/mln/core/complex_faces_iter.hh new file mode 100644 index 0000000..ea86f6f --- /dev/null +++ b/milena/mln/core/complex_faces_iter.hh @@ -0,0 +1,262 @@ +// 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 +// 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. +// reasons why the executable file might be covered by the GNU General +// Public License. + +#ifndef MLN_CORE_COMPLEX_FACES_ITER_HH +# define MLN_CORE_COMPLEX_FACES_ITER_HH + +/// \file mln/core/complex_faces_iter.hh +/// \brief Definition of forward and backward iterators on the n-faces +/// of a complex. + +# include <mln/core/internal/complex_iter_base.hh> + +/* FIXME: Should we drop N from the signature of these iterators? + I.e., have N be dynamic? Or better: provide other iterators where + N is dynamic? */ + + +namespace mln +{ + + /*--------------------------------. + | complex_faces_fwd_iter_<N, D>. | + `--------------------------------*/ + + /// \brief Forward iterator on all the faces of a mln::complex<D>. + /// + /// \arg \p N The dimension of the face associated to this iterator. + /// \arg \p D The dimension of the complex this iterator belongs to. + template <unsigned N, unsigned D> + class complex_faces_fwd_iter_ + : public internal::complex_iter_base_< any_face_handle<D>, + complex_faces_fwd_iter_<N, D> > + { + public: + /// Type of associated face. + typedef any_face_handle<D> face; + + private: + typedef complex_faces_fwd_iter_<N, D> self_; + typedef internal::complex_iter_base_< face, self_ > super_; + + public: + using super_::is_valid; + using super_::invalidate; + + public: + /// Construction and assignment. + /// \{ + complex_faces_fwd_iter_(); + // FIXME: See comment in internal::complex_iter_base_'s default ctor + complex_faces_fwd_iter_(complex<D>& c); + /// \} + + /// Manipulation. + /// \{ + /// Test if the iterator is valid. + void start(); + /// Go to the next point. + void next_(); + /// \} + + private: + using super_::face_; + }; + + + /*--------------------------------. + | complex_faces_bkd_iter_<N, D>. | + `--------------------------------*/ + + /// \brief Backward iterator on all the faces of a mln::complex<D>. + /// + /// \arg \p N The dimension of the face associated to this iterator. + /// \arg \p D The dimension of the complex this iterator belongs to. + template <unsigned N, unsigned D> + class complex_faces_bkd_iter_ + : public internal::complex_iter_base_< any_face_handle<D>, + complex_faces_bkd_iter_<N, D> > + { + public: + /// Type of associated face. + typedef any_face_handle<D> face; + + private: + typedef complex_faces_bkd_iter_<N, D> self_; + typedef internal::complex_iter_base_< face, self_ > super_; + + public: + using super_::is_valid; + using super_::invalidate; + + public: + /// Construction and assignment. + /// \{ + complex_faces_bkd_iter_(); + // FIXME: See comment in internal::complex_iter_base_'s default ctor + complex_faces_bkd_iter_(complex<D>& c); + /// \} + + /// Manipulation. + /// \{ + /// Start an iteration. + void start(); + /// Go to the next point. + void next_(); + /// \} + + private: + using super_::face_; + }; + + + +# ifndef MLN_INCLUDE_ONLY + + /*--------------------------------. + | complex_faces_fwd_iter_<N, D>. | + `--------------------------------*/ + + template <unsigned N, unsigned D> + inline + complex_faces_fwd_iter_<N, D>::complex_faces_fwd_iter_() + : super_() + { + // Ensure N is compatible with D. + metal::bool_< N <= D >::check(); + face_.set_n(N); + mln_postcondition(!is_valid()); + } + + template <unsigned N, unsigned D> + inline + complex_faces_fwd_iter_<N, D>::complex_faces_fwd_iter_(complex<D>& c) + : super_(c) + { + // Ensure N is compatible with D. + metal::bool_< N <= D >::check(); + face_.set_n(N); + mln_postcondition(!is_valid()); + } + + template <unsigned N, unsigned D> + inline + void + complex_faces_fwd_iter_<N, D>::start() + { + face_.set_face_id(0u); + } + + template <unsigned N, unsigned D> + inline + void + complex_faces_fwd_iter_<N, D>::next_() + { + if (is_valid()) + { + unsigned face_id = face_.face_id(); + if (face_id + 1 < face_.cplx().template nfaces<N>()) + /* FIXME: Provide accessor any_face_handle::face_id() + returning a mutable reference? This way, we could just + write + + ++face_.face_id(); + + instead of the following. + + Or add {inc,add}_face_id() services. */ + face_.set_face_id(face_id + 1); + else + invalidate(); + } + } + + + /*--------------------------------. + | complex_faces_bkd_iter_<N, D>. | + `--------------------------------*/ + + template <unsigned N, unsigned D> + inline + complex_faces_bkd_iter_<N, D>::complex_faces_bkd_iter_() + : super_() + { + // Ensure N is compatible with D. + metal::bool_< N <= D >::check(); + face_.set_n(N); + mln_postcondition(!is_valid()); + } + + template <unsigned N, unsigned D> + inline + complex_faces_bkd_iter_<N, D>::complex_faces_bkd_iter_(complex<D>& c) + : super_(c) + { + // Ensure N is compatible with D. + metal::bool_< N <= D >::check(); + face_.set_n(N); + mln_postcondition(!is_valid()); + } + + template <unsigned N, unsigned D> + inline + void + complex_faces_bkd_iter_<N, D>::start() + { + face_.set_face_id(face_.cplx().template nfaces<N>() - 1); + } + + template <unsigned N, unsigned D> + inline + void + complex_faces_bkd_iter_<N, D>::next_() + { + if (is_valid()) + { + unsigned face_id = face_.face_id(); + if (face_id > 0) + /* FIXME: Provide accessor any_face_handle::face_id() + returning a mutable reference? This way, we could just + write + + ++face_.face_id(); + + instead of the following. + + Or add {inc,add}_face_id() services. */ + face_.set_face_id(face_id - 1); + else + invalidate(); + } + } + +# endif // ! MLN_INCLUDE_ONLY + +} // end of mln + + +#endif // ! MLN_CORE_COMPLEX_FACES_ITER_HH -- 1.6.0.1
participants (1)
-
Roland Levillain