utree3.cpp 6.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197
  1. // Copyright (c) 2001-2011 Hartmut Kaiser
  2. // Copyright (c) 2001-2011 Joel de Guzman
  3. // Copyright (c) 2010 Bryce Lelbach
  4. //
  5. // Distributed under the Boost Software License, Version 1.0. (See accompanying
  6. // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  7. #include <boost/config/warning_disable.hpp>
  8. #include <boost/detail/lightweight_test.hpp>
  9. #include <boost/spirit/include/qi.hpp>
  10. #include <boost/spirit/include/support_utree.hpp>
  11. #include <boost/mpl/print.hpp>
  12. #include <sstream>
  13. #include "test.hpp"
  14. inline bool check(boost::spirit::utree const& val, std::string expected)
  15. {
  16. std::stringstream s;
  17. s << val;
  18. if (s.str() == expected + " ")
  19. return true;
  20. std::cerr << "got result: " << s.str()
  21. << ", expected: " << expected << std::endl;
  22. return false;
  23. }
  24. int main()
  25. {
  26. using spirit_test::test_attr;
  27. using boost::spirit::utree;
  28. using boost::spirit::utree_type;
  29. using boost::spirit::utf8_string_range_type;
  30. using boost::spirit::utf8_symbol_type;
  31. using boost::spirit::utf8_string_type;
  32. using boost::spirit::qi::real_parser;
  33. using boost::spirit::qi::strict_real_policies;
  34. using boost::spirit::qi::digit;
  35. using boost::spirit::qi::char_;
  36. using boost::spirit::qi::string;
  37. using boost::spirit::qi::int_;
  38. using boost::spirit::qi::double_;
  39. using boost::spirit::qi::space;
  40. using boost::spirit::qi::space_type;
  41. using boost::spirit::qi::rule;
  42. using boost::spirit::qi::as;
  43. using boost::spirit::qi::lexeme;
  44. // alternatives
  45. {
  46. typedef real_parser<double, strict_real_policies<double> >
  47. strict_double_type;
  48. strict_double_type const strict_double = strict_double_type();
  49. utree ut;
  50. BOOST_TEST(test_attr("10", strict_double | int_, ut) &&
  51. ut.which() == utree_type::int_type && check(ut, "10"));
  52. ut.clear();
  53. BOOST_TEST(test_attr("10.2", strict_double | int_, ut) &&
  54. ut.which() == utree_type::double_type && check(ut, "10.2"));
  55. rule<char const*, boost::variant<int, double>()> r1 = strict_double | int_;
  56. ut.clear();
  57. BOOST_TEST(test_attr("10", r1, ut) &&
  58. ut.which() == utree_type::int_type && check(ut, "10"));
  59. ut.clear();
  60. BOOST_TEST(test_attr("10.2", r1, ut) &&
  61. ut.which() == utree_type::double_type && check(ut, "10.2"));
  62. rule<char const*, utree()> r2 = strict_double | int_;
  63. ut.clear();
  64. BOOST_TEST(test_attr("10", r2, ut) &&
  65. ut.which() == utree_type::int_type && check(ut, "10"));
  66. ut.clear();
  67. BOOST_TEST(test_attr("10.2", r2, ut) &&
  68. ut.which() == utree_type::double_type && check(ut, "10.2"));
  69. rule<char const*, utree::list_type()> r3 = strict_double | int_;
  70. ut.clear();
  71. BOOST_TEST(test_attr("10", r3, ut) &&
  72. ut.which() == utree_type::list_type && check(ut, "( 10 )"));
  73. ut.clear();
  74. BOOST_TEST(test_attr("10.2", r3, ut) &&
  75. ut.which() == utree_type::list_type && check(ut, "( 10.2 )"));
  76. }
  77. // optionals
  78. {
  79. utree ut;
  80. BOOST_TEST(test_attr("x", -char_, ut));
  81. BOOST_TEST(ut.which() == utree_type::string_type);
  82. BOOST_TEST(check(ut, "\"x\""));
  83. ut.clear();
  84. BOOST_TEST(test_attr("", -char_, ut));
  85. BOOST_TEST(ut.which() == utree_type::invalid_type);
  86. BOOST_TEST(check(ut, "<invalid>"));
  87. ut.clear();
  88. BOOST_TEST(test_attr("1x", int_ >> -char_, ut));
  89. BOOST_TEST(ut.which() == utree_type::list_type);
  90. BOOST_TEST(check(ut, "( 1 \"x\" )"));
  91. ut.clear();
  92. BOOST_TEST(test_attr("1", int_ >> -char_, ut));
  93. BOOST_TEST(ut.which() == utree_type::list_type);
  94. BOOST_TEST(check(ut, "( 1 )"));
  95. ut.clear();
  96. BOOST_TEST(test_attr("1x", -int_ >> char_, ut));
  97. BOOST_TEST(ut.which() == utree_type::list_type);
  98. BOOST_TEST(check(ut, "( 1 \"x\" )"));
  99. ut.clear();
  100. BOOST_TEST(test_attr("x", -int_ >> char_, ut));
  101. BOOST_TEST(ut.which() == utree_type::list_type);
  102. BOOST_TEST(check(ut, "( \"x\" )"));
  103. ut.clear();
  104. rule<char const*, utree::list_type()> r1 = int_ >> -char_;
  105. BOOST_TEST(test_attr("1x", r1, ut));
  106. BOOST_TEST(ut.which() == utree_type::list_type);
  107. BOOST_TEST(check(ut, "( 1 \"x\" )"));
  108. ut.clear();
  109. BOOST_TEST(test_attr("1", r1, ut));
  110. BOOST_TEST(ut.which() == utree_type::list_type);
  111. BOOST_TEST(check(ut, "( 1 )"));
  112. ut.clear();
  113. rule<char const*, utree::list_type()> r2 = -int_ >> char_;
  114. BOOST_TEST(test_attr("1x", r2, ut));
  115. BOOST_TEST(ut.which() == utree_type::list_type);
  116. BOOST_TEST(check(ut, "( 1 \"x\" )"));
  117. ut.clear();
  118. BOOST_TEST(test_attr("x", r2, ut));
  119. BOOST_TEST(ut.which() == utree_type::list_type);
  120. BOOST_TEST(check(ut, "( \"x\" )"));
  121. ut.clear();
  122. rule<char const*, utree()> r3 = int_;
  123. BOOST_TEST(test_attr("1", -r3, ut));
  124. BOOST_TEST(ut.which() == utree_type::int_type);
  125. BOOST_TEST(check(ut, "1"));
  126. ut.clear();
  127. BOOST_TEST(test_attr("", -r3, ut));
  128. BOOST_TEST(ut.which() == utree_type::invalid_type);
  129. BOOST_TEST(check(ut, "<invalid>"));
  130. ut.clear();
  131. }
  132. // as_string
  133. {
  134. using boost::spirit::qi::as_string;
  135. utree ut;
  136. BOOST_TEST(test_attr("xy", as_string[char_ >> char_], ut) &&
  137. ut.which() == utree_type::string_type && check(ut, "\"xy\""));
  138. ut.clear();
  139. BOOST_TEST(test_attr("ab1.2", as_string[*~digit] >> double_, ut) &&
  140. ut.which() == utree_type::list_type && check(ut, "( \"ab\" 1.2 )"));
  141. ut.clear();
  142. BOOST_TEST(test_attr("xy", as_string[*char_], ut) &&
  143. ut.which() == utree_type::string_type && check(ut, "\"xy\""));
  144. ut.clear();
  145. BOOST_TEST(test_attr("x,y", as_string[char_ >> ',' >> char_], ut) &&
  146. ut.which() == utree_type::string_type && check(ut, "\"xy\""));
  147. ut.clear();
  148. BOOST_TEST(test_attr("x,y", char_ >> ',' >> char_, ut) &&
  149. ut.which() == utree_type::list_type && check(ut, "( \"x\" \"y\" )"));
  150. ut.clear();
  151. BOOST_TEST(test_attr("a,b1.2", as_string[~digit % ','] >> double_, ut) &&
  152. ut.which() == utree_type::list_type && check(ut, "( \"ab\" 1.2 )"));
  153. ut.clear();
  154. BOOST_TEST(test_attr("a,b1.2", ~digit % ',' >> double_, ut) &&
  155. ut.which() == utree_type::list_type && check(ut, "( \"a\" \"b\" 1.2 )"));
  156. ut.clear();
  157. }
  158. return boost::report_errors();
  159. }