buffering_input_iterator_policy.hpp 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128
  1. // Copyright (c) 2001 Daniel C. Nuffer
  2. // Copyright (c) 2001-2011 Hartmut Kaiser
  3. //
  4. // Distributed under the Boost Software License, Version 1.0. (See accompanying
  5. // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  6. #if !defined(BOOST_SPIRIT_BUFFERING_ITERATOR_INPUT_ITERATOR_POLICY_MAR_04_2010_1224AM)
  7. #define BOOST_SPIRIT_BUFFERING_ITERATOR_INPUT_ITERATOR_POLICY_MAR_04_2010_1224AM
  8. #include <boost/spirit/home/support/iterators/multi_pass_fwd.hpp>
  9. #include <boost/spirit/home/support/iterators/detail/multi_pass.hpp>
  10. #include <boost/spirit/home/support/iterators/detail/input_iterator_policy.hpp>
  11. #include <boost/assert.hpp>
  12. #include <iterator> // for std::iterator_traits
  13. namespace boost { namespace spirit { namespace iterator_policies
  14. {
  15. ///////////////////////////////////////////////////////////////////////////
  16. // class input_iterator
  17. //
  18. // Implementation of the InputPolicy used by multi_pass, this is different
  19. // from the input_iterator policy only as it is buffering the last input
  20. // character to allow returning it by reference. This is needed for
  21. // wrapping iterators not buffering the last item (such as the
  22. // std::istreambuf_iterator). Unfortunately there is no way to
  23. // automatically figure this out at compile time.
  24. //
  25. // The buffering_input_iterator encapsulates an input iterator of type T
  26. ///////////////////////////////////////////////////////////////////////////
  27. struct buffering_input_iterator
  28. {
  29. ///////////////////////////////////////////////////////////////////////
  30. template <typename T>
  31. class unique // : public detail::default_input_policy
  32. {
  33. private:
  34. typedef
  35. typename std::iterator_traits<T>::value_type
  36. result_type;
  37. public:
  38. typedef
  39. typename std::iterator_traits<T>::difference_type
  40. difference_type;
  41. typedef
  42. typename std::iterator_traits<T>::difference_type
  43. distance_type;
  44. typedef
  45. typename std::iterator_traits<T>::pointer
  46. pointer;
  47. typedef result_type& reference;
  48. typedef result_type value_type;
  49. protected:
  50. unique() {}
  51. explicit unique(T x) {}
  52. void swap(unique&) {}
  53. public:
  54. template <typename MultiPass>
  55. static void destroy(MultiPass&) {}
  56. template <typename MultiPass>
  57. static typename MultiPass::reference get_input(MultiPass& mp)
  58. {
  59. return mp.shared()->get_input();
  60. }
  61. template <typename MultiPass>
  62. static void advance_input(MultiPass& mp)
  63. {
  64. BOOST_ASSERT(0 != mp.shared());
  65. mp.shared()->advance_input();
  66. }
  67. // test, whether we reached the end of the underlying stream
  68. template <typename MultiPass>
  69. static bool input_at_eof(MultiPass const& mp)
  70. {
  71. static T const end_iter;
  72. return mp.shared()->input_ == end_iter;
  73. }
  74. template <typename MultiPass>
  75. static bool input_is_valid(MultiPass const& mp, value_type const& t)
  76. {
  77. return mp.shared()->input_is_valid_;
  78. }
  79. // no unique data elements
  80. };
  81. ///////////////////////////////////////////////////////////////////////
  82. template <typename T>
  83. struct shared
  84. {
  85. typedef
  86. typename std::iterator_traits<T>::value_type
  87. result_type;
  88. explicit shared(T const& input)
  89. : input_(input), curtok_(0), input_is_valid_(false) {}
  90. void advance_input()
  91. {
  92. ++input_;
  93. input_is_valid_ = false;
  94. }
  95. result_type& get_input()
  96. {
  97. if (!input_is_valid_) {
  98. curtok_ = *input_;
  99. input_is_valid_ = true;
  100. }
  101. return curtok_;
  102. }
  103. T input_;
  104. result_type curtok_;
  105. bool input_is_valid_;
  106. };
  107. };
  108. }}}
  109. #endif