#ifndef function_input_iterator_H #define function_input_iterator_H #include #include #include #include namespace boost { template class function_input_iterator : public boost::iterator_facade< function_input_iterator, typename boost::remove_reference::type::result_type, boost::forward_traversal_tag, typename boost::remove_reference::type::result_type > { public: typedef typename boost::iterator_facade< function_input_iterator, typename boost::remove_reference::type::result_type, boost::forward_traversal_tag, typename boost::remove_reference::type::result_type> super_t; typedef typename super_t::difference_type difference_type; typedef typename super_t::reference reference; typedef typename super_t::value_type value_type; explicit function_input_iterator() {} explicit function_input_iterator (FUNC _f, int _cnt=0) : f (_f), cnt (_cnt) {} private: friend class boost::iterator_core_access; void increment () { cache = f(); ++cnt; } // void advance (difference_type n) { // assert (n >= 0); // for (int i = 0; i < n; i++) // increment(); // } difference_type distance_to (function_input_iterator const& y) const { return -(cnt - y.cnt); } bool equal (function_input_iterator const& y) const { return distance_to (y) == 0; } reference dereference() const { if (!cache) cache = f(); return cache.get(); } private: mutable FUNC f; mutable boost::optional cache; int cnt; }; template function_input_iterator make_function_input_iterator(FUNC f, int cnt=0) { return function_input_iterator (f, cnt); } } //namespace boost #endif