assert_word_matcher.hpp 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125
  1. ///////////////////////////////////////////////////////////////////////////////
  2. // assert_word_matcher.hpp
  3. //
  4. // Copyright 2008 Eric Niebler. Distributed under the Boost
  5. // Software License, Version 1.0. (See accompanying file
  6. // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  7. #ifndef BOOST_XPRESSIVE_DETAIL_CORE_MATCHER_ASSERT_WORD_MATCHER_HPP_EAN_10_04_2005
  8. #define BOOST_XPRESSIVE_DETAIL_CORE_MATCHER_ASSERT_WORD_MATCHER_HPP_EAN_10_04_2005
  9. // MS compatible compilers support #pragma once
  10. #if defined(_MSC_VER)
  11. # pragma once
  12. #endif
  13. #include <boost/assert.hpp>
  14. #include <boost/xpressive/detail/detail_fwd.hpp>
  15. #include <boost/xpressive/detail/core/quant_style.hpp>
  16. #include <boost/xpressive/detail/utility/ignore_unused.hpp>
  17. #include <boost/xpressive/detail/core/state.hpp>
  18. namespace boost { namespace xpressive { namespace detail
  19. {
  20. ///////////////////////////////////////////////////////////////////////////////
  21. // word_boundary
  22. //
  23. template<typename IsBoundary>
  24. struct word_boundary
  25. {
  26. template<typename BidiIter>
  27. static bool eval(bool prevword, bool thisword, match_state<BidiIter> &state)
  28. {
  29. if((state.flags_.match_not_bow_ && state.bos()) || (state.flags_.match_not_eow_ && state.eos()))
  30. {
  31. return !IsBoundary::value;
  32. }
  33. return IsBoundary::value == (prevword != thisword);
  34. }
  35. };
  36. ///////////////////////////////////////////////////////////////////////////////
  37. // word_begin
  38. //
  39. struct word_begin
  40. {
  41. template<typename BidiIter>
  42. static bool eval(bool prevword, bool thisword, match_state<BidiIter> &state)
  43. {
  44. if(state.flags_.match_not_bow_ && state.bos())
  45. {
  46. return false;
  47. }
  48. return !prevword && thisword;
  49. }
  50. };
  51. ///////////////////////////////////////////////////////////////////////////////
  52. // word_end
  53. //
  54. struct word_end
  55. {
  56. template<typename BidiIter>
  57. static bool eval(bool prevword, bool thisword, match_state<BidiIter> &state)
  58. {
  59. if(state.flags_.match_not_eow_ && state.eos())
  60. {
  61. return false;
  62. }
  63. return prevword && !thisword;
  64. }
  65. };
  66. ///////////////////////////////////////////////////////////////////////////////
  67. // assert_word_matcher
  68. //
  69. template<typename Cond, typename Traits>
  70. struct assert_word_matcher
  71. : quant_style_assertion
  72. {
  73. typedef typename Traits::char_type char_type;
  74. typedef typename Traits::char_class_type char_class_type;
  75. assert_word_matcher(Traits const &tr)
  76. : word_(lookup_classname(tr, "w"))
  77. {
  78. BOOST_ASSERT(0 != this->word_);
  79. }
  80. assert_word_matcher(char_class_type word)
  81. : word_(word)
  82. {}
  83. bool is_word(Traits const &tr, char_type ch) const
  84. {
  85. detail::ignore_unused(tr);
  86. return tr.isctype(tr.translate(ch), this->word_);
  87. }
  88. template<typename BidiIter, typename Next>
  89. bool match(match_state<BidiIter> &state, Next const &next) const
  90. {
  91. BidiIter cur = state.cur_;
  92. bool const thisword = !state.eos() && this->is_word(traits_cast<Traits>(state), *cur);
  93. bool const prevword = (!state.bos() || state.flags_.match_prev_avail_)
  94. && this->is_word(traits_cast<Traits>(state), *--cur);
  95. return Cond::eval(prevword, thisword, state) && next.match(state);
  96. }
  97. char_class_type word() const
  98. {
  99. return this->word_;
  100. }
  101. private:
  102. char_class_type word_;
  103. };
  104. }}}
  105. #endif