for_tests.cpp 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192
  1. /*=============================================================================
  2. Copyright (c) 2003 Martin Wille
  3. http://spirit.sourceforge.net/
  4. Use, modification and distribution is subject to the Boost Software
  5. License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
  6. http://www.boost.org/LICENSE_1_0.txt)
  7. =============================================================================*/
  8. // vi:ts=4:sw=4:et
  9. // Tests for spirit::for_p
  10. // [13-Jan-2003]
  11. ////////////////////////////////////////////////////////////////////////////////
  12. #include <iostream>
  13. #include <cstring>
  14. #include <string>
  15. #include <boost/spirit/include/classic_core.hpp>
  16. #include <boost/spirit/include/classic_assign_actor.hpp>
  17. #include <boost/spirit/include/classic_for.hpp>
  18. #include <boost/ref.hpp>
  19. #include "impl/string_length.hpp"
  20. namespace local
  21. {
  22. template <typename T>
  23. struct var_wrapper
  24. : public ::boost::reference_wrapper<T>
  25. {
  26. typedef ::boost::reference_wrapper<T> parent;
  27. explicit inline var_wrapper(T& t) : parent(t) {}
  28. inline T& operator()() const { return parent::get(); }
  29. };
  30. template <typename T>
  31. inline var_wrapper<T>
  32. var(T& t)
  33. {
  34. return var_wrapper<T>(t);
  35. }
  36. }
  37. namespace
  38. {
  39. template <typename T>
  40. class add_actor
  41. {
  42. public:
  43. explicit add_actor(T &ref_) : ref(ref_) {}
  44. template <typename T2>
  45. void operator()(T2 const &val) const
  46. { ref += val; }
  47. private:
  48. T& ref;
  49. };
  50. template <typename T>
  51. inline add_actor<T> const
  52. add(T& ref)
  53. {
  54. return add_actor<T>(ref);
  55. }
  56. }
  57. typedef ::BOOST_SPIRIT_CLASSIC_NS::rule<> rule_t;
  58. unsigned int test_count = 0;
  59. unsigned int error_count = 0;
  60. unsigned int iterations_performed;
  61. unsigned int iterations_desired;
  62. std::string input_matched;
  63. //static const unsigned int kError = 999;
  64. static const bool good = true;
  65. static const bool bad = false;
  66. rule_t for_rule;
  67. rule_t for_rule2;
  68. void
  69. test_for
  70. (
  71. char const *s,
  72. bool succeed,
  73. rule_t const &r,
  74. unsigned int iterations_expected
  75. )
  76. {
  77. using namespace std;
  78. ++test_count;
  79. iterations_performed = 0;
  80. ::BOOST_SPIRIT_CLASSIC_NS::parse_info<> m = ::BOOST_SPIRIT_CLASSIC_NS::parse(s, s + test_impl::string_length(s), r);
  81. bool result = (succeed==m.full)?good:bad;
  82. if (m.full && (m.length != test_impl::string_length(s)))
  83. result = bad;
  84. result &= iterations_expected == iterations_performed;
  85. if (result==good)
  86. cout << "PASSED";
  87. else
  88. {
  89. ++error_count;
  90. cout << "FAILED";
  91. }
  92. cout << ": \"" << s << "\" ==> ";
  93. if (!m.full)
  94. cout << "<error>";
  95. else
  96. cout << '"' << input_matched << '"';
  97. cout << " " << iterations_performed << " of "
  98. << iterations_desired << " iterations\n";
  99. }
  100. namespace
  101. {
  102. void zero() { iterations_performed = 0; }
  103. struct inc
  104. {
  105. inline void operator()() const { ++iterations_performed; }
  106. };
  107. struct cmp
  108. {
  109. inline bool operator()() const
  110. {
  111. return iterations_performed<iterations_desired;
  112. }
  113. };
  114. }
  115. int
  116. main()
  117. {
  118. using namespace std;
  119. using BOOST_SPIRIT_CLASSIC_NS::uint_p;
  120. using BOOST_SPIRIT_CLASSIC_NS::for_p;
  121. using BOOST_SPIRIT_CLASSIC_NS::assign_a;
  122. #if qDebug
  123. SPIRIT_DEBUG_RULE(for_rule);
  124. SPIRIT_DEBUG_RULE(for_rule2);
  125. #endif
  126. for_rule
  127. = uint_p[assign_a(iterations_desired)] >> ':'
  128. >> for_p(&zero, cmp(), inc())["xy"]
  129. [assign_a(input_matched)]
  130. ;
  131. for_rule2
  132. = for_p(&zero, '.', inc())["xy"]
  133. [assign_a(input_matched)]
  134. ;
  135. cout << "/////////////////////////////////////////////////////////\n";
  136. cout << "\n";
  137. cout << " for_p test\n";
  138. cout << "\n";
  139. cout << "/////////////////////////////////////////////////////////\n";
  140. cout << "\n";
  141. test_for("3:xyxyxy", true, for_rule, 3);
  142. test_for("3:", false, for_rule, 0);
  143. test_for("3:xyxy", false, for_rule, 2);
  144. test_for("3:xyxyxyxy", false, for_rule, 3);
  145. test_for(".xy.xy.xy", true, for_rule2, 3);
  146. test_for(".xy.xy.xy.", false, for_rule2, 3);
  147. std::cout << "\n ";
  148. if (error_count==0)
  149. cout << "All " << test_count << " for_p-tests passed.\n"
  150. << "Test concluded successfully\n";
  151. else
  152. cout << error_count << " of " << test_count << " for_p-tests failed\n"
  153. << "Test failed\n";
  154. return error_count!=0;
  155. }