#ifndef __CXXMPH_HOLLOW_ITERATOR_H__ #define __CXXMPH_HOLLOW_ITERATOR_H__ #include namespace cxxmph { using std::vector; template struct is_empty { public: is_empty() : c_(NULL), p_(NULL) {}; is_empty(const container_type* c, const vector* p) : c_(c), p_(p) {}; bool operator()(typename container_type::const_iterator it) const { if (it == c_->end()) return false; return !(*p_)[it - c_->begin()]; } private: const container_type* c_; const vector* p_; }; template struct hollow_iterator_base : public std::iterator { public: typedef hollow_iterator_base& self_type; typedef self_type& self_reference; typedef typename iterator::reference reference; typedef typename iterator::pointer pointer; hollow_iterator_base() : it_(), empty_() { } hollow_iterator_base(iterator it, is_empty empty) : it_(it), empty_(empty) { advance(); } hollow_iterator_base(const self_type& rhs) { it_ = rhs.it_; empty_ = rhs.empty_; } template hollow_iterator_base(const hollow_iterator_base& rhs) { it_ = rhs.it_; empty_ = rhs.empty_; } reference operator*() { return *it_; } pointer operator->() { return &(*it_); } self_reference operator++() { ++it_; advance(); return *this; } // self_type operator++() { auto tmp(*this); ++tmp; return tmp; } template bool operator==(const hollow_iterator_base& rhs) { return rhs.it_ == it_; } template bool operator!=(const hollow_iterator_base& rhs) { return rhs.it_ != it_; } // should be friend iterator it_; is_empty empty_; private: void advance() { while (empty_(it_)) ++it_; } }; template auto make_hollow( container_type* v, vector* p, iterator it) -> hollow_iterator_base> { return hollow_iterator_base>( it, is_empty(v, p)); } } // namespace cxxmph #endif // __CXXMPH_HOLLOW_ITERATOR_H__