zip_iterator.hpp
来自「CGAL is a collaborative effort of severa」· HPP 代码 · 共 600 行 · 第 1/2 页
HPP
600 行
#ifdef BOOST_TUPLE_ALGO_DISPATCH template<typename Tuple, typename Fun> Fun tuple_for_each( Tuple& t, Fun f ) { return tuple_for_each_impl(t, f, 1); }#endif // Equality of tuples. NOTE: "==" for tuples currently (7/2003) // has problems under some compilers, so I just do my own. // No point in bringing in a bunch of #ifdefs here. This is // going to go away with the next tuple implementation anyway. // bool tuple_equal(tuples::null_type, tuples::null_type) { return true; } template<typename Tuple1, typename Tuple2> bool tuple_equal( Tuple1 const& t1, Tuple2 const& t2 ) { return t1.get_head() == t2.get_head() && tuple_equal(t1.get_tail(), t2.get_tail()); } } // // end namespace tuple_impl_specific template<typename Iterator> struct iterator_reference { typedef typename iterator_traits<Iterator>::reference type; };#ifdef BOOST_MPL_CFG_NO_FULL_LAMBDA_SUPPORT // Hack because BOOST_MPL_AUX_LAMBDA_SUPPORT doesn't seem to work // out well. Instantiating the nested apply template also // requires instantiating iterator_traits on the // placeholder. Instead we just specialize it as a metafunction // class. template<> struct iterator_reference<mpl::_1> { template <class T> struct apply : iterator_reference<T> {}; };#endif // Metafunction to obtain the type of the tuple whose element types // are the reference types of an iterator tuple. // template<typename IteratorTuple> struct tuple_of_references : tuple_impl_specific::tuple_meta_transform< IteratorTuple, iterator_reference<mpl::_1> > { }; // Metafunction to obtain the minimal traversal tag in a tuple // of iterators. // template<typename IteratorTuple> struct minimum_traversal_category_in_iterator_tuple { typedef typename tuple_impl_specific::tuple_meta_transform< IteratorTuple , iterator_traversal<> >::type tuple_of_traversal_tags; typedef typename tuple_impl_specific::tuple_meta_accumulate< tuple_of_traversal_tags , minimum_category<> , random_access_traversal_tag >::type type; };#if BOOST_WORKAROUND(BOOST_MSVC, == 1200) // ETI workaround template <> struct minimum_traversal_category_in_iterator_tuple<int> { typedef int type; };#endif // We need to call tuple_meta_accumulate with mpl::and_ as the // accumulating functor. To this end, we need to wrap it into // a struct that has exactly two arguments (that is, template // parameters) and not five, like mpl::and_ does. // template<typename Arg1, typename Arg2> struct and_with_two_args : mpl::and_<Arg1, Arg2> { }; # ifdef BOOST_MPL_CFG_NO_FULL_LAMBDA_SUPPORT // Hack because BOOST_MPL_AUX_LAMBDA_SUPPORT doesn't seem to work // out well. In this case I think it's an MPL bug template<> struct and_with_two_args<mpl::_1,mpl::_2> { template <class A1, class A2> struct apply : mpl::and_<A1,A2> {}; };# endif /////////////////////////////////////////////////////////////////// // // Class zip_iterator_base // // Builds and exposes the iterator facade type from which the zip // iterator will be derived. // template<typename IteratorTuple> struct zip_iterator_base { private: // Reference type is the type of the tuple obtained from the // iterators' reference types. typedef typename detail::tuple_of_references<IteratorTuple>::type reference; // Value type is the same as reference type. typedef reference value_type; // Difference type is the first iterator's difference type typedef typename iterator_traits< typename tuples::element<0, IteratorTuple>::type >::difference_type difference_type; // Traversal catetgory is the minimum traversal category in the // iterator tuple. typedef typename detail::minimum_traversal_category_in_iterator_tuple< IteratorTuple >::type traversal_category; public: // The iterator facade type from which the zip iterator will // be derived. typedef iterator_facade< zip_iterator<IteratorTuple>, value_type, traversal_category, reference, difference_type > type; }; template <> struct zip_iterator_base<int> { typedef int type; }; } ///////////////////////////////////////////////////////////////////// // // zip_iterator class definition // template<typename IteratorTuple> class zip_iterator : public detail::zip_iterator_base<IteratorTuple>::type { // Typedef super_t as our base class. typedef typename detail::zip_iterator_base<IteratorTuple>::type super_t; // iterator_core_access is the iterator's best friend. friend class iterator_core_access; public: // Construction // ============ // Default constructor zip_iterator() { } // Constructor from iterator tuple zip_iterator(IteratorTuple iterator_tuple) : m_iterator_tuple(iterator_tuple) { } // Copy constructor template<typename OtherIteratorTuple> zip_iterator( const zip_iterator<OtherIteratorTuple>& other, typename enable_if_convertible< OtherIteratorTuple, IteratorTuple >::type* = 0 ) : m_iterator_tuple(other.get_iterator_tuple()) {} // Get method for the iterator tuple. const IteratorTuple& get_iterator_tuple() const { return m_iterator_tuple; } private: // Implementation of Iterator Operations // ===================================== // Dereferencing returns a tuple built from the dereferenced // iterators in the iterator tuple. typename super_t::reference dereference() const { return detail::tuple_impl_specific::tuple_transform( get_iterator_tuple(), detail::dereference_iterator() ); } // Two zip iterators are equal if all iterators in the iterator // tuple are equal. NOTE: It should be possible to implement this // as // // return get_iterator_tuple() == other.get_iterator_tuple(); // // but equality of tuples currently (7/2003) does not compile // under several compilers. No point in bringing in a bunch // of #ifdefs here. // template<typename OtherIteratorTuple> bool equal(const zip_iterator<OtherIteratorTuple>& other) const { return detail::tuple_impl_specific::tuple_equal( get_iterator_tuple(), other.get_iterator_tuple() ); } // Advancing a zip iterator means to advance all iterators in the // iterator tuple. void advance(typename super_t::difference_type n) { detail::tuple_impl_specific::tuple_for_each( m_iterator_tuple, detail::advance_iterator<BOOST_DEDUCED_TYPENAME super_t::difference_type>(n) ); } // Incrementing a zip iterator means to increment all iterators in // the iterator tuple. void increment() { detail::tuple_impl_specific::tuple_for_each( m_iterator_tuple, detail::increment_iterator() ); } // Decrementing a zip iterator means to decrement all iterators in // the iterator tuple. void decrement() { detail::tuple_impl_specific::tuple_for_each( m_iterator_tuple, detail::decrement_iterator() ); } // Distance is calculated using the first iterator in the tuple. template<typename OtherIteratorTuple> typename super_t::difference_type distance_to( const zip_iterator<OtherIteratorTuple>& other ) const { return boost::tuples::get<0>(other.get_iterator_tuple()) - boost::tuples::get<0>(this->get_iterator_tuple()); } // Data Members // ============ // The iterator tuple. IteratorTuple m_iterator_tuple; }; // Make function for zip iterator // template<typename IteratorTuple> zip_iterator<IteratorTuple> make_zip_iterator(IteratorTuple t) { return zip_iterator<IteratorTuple>(t); }}#endif
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?