yat  0.8.3pre
StrideIterator.h
00001 #ifndef _theplu_yat_utility_stride_iterator_
00002 #define _theplu_yat_utility_stride_iterator_
00003 
00004 // $Id: StrideIterator.h 2365 2010-12-06 00:40:13Z peter $
00005 
00006 /*
00007   Copyright (C) 2007, 2008 Jari Häkkinen, Peter Johansson
00008   Copyright (C) 2010 Peter Johansson
00009 
00010   This file is part of the yat library, http://dev.thep.lu.se/yat
00011 
00012   The yat library is free software; you can redistribute it and/or
00013   modify it under the terms of the GNU General Public License as
00014   published by the Free Software Foundation; either version 3 of the
00015   License, or (at your option) any later version.
00016 
00017   The yat library is distributed in the hope that it will be useful,
00018   but WITHOUT ANY WARRANTY; without even the implied warranty of
00019   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
00020   General Public License for more details.
00021 
00022   You should have received a copy of the GNU General Public License
00023   along with yat. If not, see <http://www.gnu.org/licenses/>.
00024 */
00025 
00026 #include <boost/concept_check.hpp>
00027 #include <boost/iterator/iterator_adaptor.hpp>
00028 
00029 namespace theplu {
00030 namespace yat {
00031 namespace utility {
00032 
00044   template<typename RandomAccessIterator>
00045   class StrideIterator 
00046     : public boost::iterator_adaptor<StrideIterator<RandomAccessIterator>
00047                                      , RandomAccessIterator
00048                                      , boost::use_default
00049       , typename std::iterator_traits<RandomAccessIterator>::iterator_category>
00050   {
00051     typedef boost::iterator_adaptor<StrideIterator<RandomAccessIterator>,
00052                                     RandomAccessIterator,
00053                                     boost::use_default,
00054       typename std::iterator_traits<RandomAccessIterator>::iterator_category>
00055     super_t;
00056 
00057   public:
00059     typedef RandomAccessIterator iterator_type;
00060 
00066     explicit StrideIterator(size_t stride=1)
00067       : StrideIterator::iterator_adaptor_(), stride_(stride) 
00068     {
00069       BOOST_CONCEPT_ASSERT((boost::RandomAccessIterator<RandomAccessIterator>));
00070     }
00071 
00075     explicit StrideIterator(RandomAccessIterator p, size_t stride=1)
00076       : StrideIterator::iterator_adaptor_(p), stride_(stride) {}
00077 
00078     
00082     StrideIterator(const StrideIterator& other)
00083       : StrideIterator::iterator_adaptor_(other.base()), stride_(other.stride()) 
00084     {}
00085 
00094     template<typename I2>
00095     StrideIterator(StrideIterator<I2> other,
00096                    typename boost::enable_if_convertible<I2
00097                    , RandomAccessIterator>::type* = 0 )
00098       : StrideIterator::iterator_adaptor_(other.base()), 
00099         stride_(other.stride()) {}
00100 
00104     StrideIterator& operator=(const StrideIterator& rhs)
00105     {
00106       stride_ = rhs.stride();
00107       this->base_reference() = rhs.base();
00108       return *this;
00109     }
00110 
00114     inline size_t stride(void) const { return stride_; }
00115 
00116   private:
00117     // to give base class access to private parts
00118     friend class boost::iterator_core_access;
00119     
00120     size_t stride_;
00121 
00122     //typedef typename StrideIterator::iterator_adaptor_::difference_type
00123     typedef typename StrideIterator::iterator_adaptor_::difference_type
00124     difference_t;
00125 
00126     void advance(typename super_t::difference_type n)
00127     { this->base_reference() += stride_*n; }
00128 
00129     void decrement(void) { this->base_reference()-=stride_; }
00130 
00131     template <class OtherIterator>
00132     typename super_t::difference_type 
00133     distance_to(const StrideIterator<OtherIterator>& other) const
00134     { 
00135       // casting to int to avoid loss of sign in numerator
00136       return (other.base() - this->base() )/static_cast<int>(stride_); 
00137     }
00138 
00139     void increment(void) { this->base_reference()+=stride_; }
00140   };
00141 
00142 }}} // of namespace utility, yat, and theplu
00143 
00144 #endif

Generated on Thu Dec 20 2012 03:12:58 for yat by  doxygen 1.8.0-20120409