getting_serious.cpp 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155
  1. // Copyright (c) 2009-2016 Vladimir Batov.
  2. // Use, modification and distribution are subject to the Boost Software License,
  3. // Version 1.0. See http://www.boost.org/LICENSE_1_0.txt.
  4. #ifdef BOOST_MSVC
  5. # pragma warning(disable : 4127) // conditional expression is constant.
  6. # pragma warning(disable : 4189) // local variable is initialized but not referenced.
  7. #endif
  8. #include <boost/convert.hpp>
  9. #include <boost/convert/stream.hpp>
  10. #include <boost/convert/lexical_cast.hpp>
  11. using std::string;
  12. using boost::convert;
  13. using boost::lexical_cast;
  14. using boost::optional;
  15. static void process_failure() {}
  16. static void log(...) {}
  17. static int fallback_function() { return -1; }
  18. //[getting_serious_default_converter
  19. struct boost::cnv::by_default : boost::cnv::cstream {};
  20. //]
  21. static
  22. void
  23. example1()
  24. {
  25. boost::cnv::cstream cnv;
  26. std::string const str = "123";
  27. std::string const str1 = "123";
  28. std::string const str2 = "123";
  29. std::string const str3 = "123";
  30. int const fallback_value = -1;
  31. {
  32. //[getting_serious_example1
  33. int i2 = convert<int>("not an int", cnv).value_or(-1); // after the call i2==-1
  34. if (i2 == -1) process_failure();
  35. //]
  36. }
  37. {
  38. //[getting_serious_example2
  39. try
  40. {
  41. int i1 = lexical_cast<int>(str); // Throws if the conversion fails.
  42. int i2 = convert<int>(str, cnv).value(); // Throws if the conversion fails.
  43. }
  44. catch (...)
  45. {
  46. process_failure();
  47. }
  48. //]
  49. }
  50. {
  51. //[getting_serious_example3
  52. optional<int> r1 = convert<int>(str1, cnv); // Does not throw on conversion failure.
  53. optional<int> r2 = convert<int>(str2, cnv); // Does not throw on conversion failure.
  54. // ...
  55. try // Delayed processing of potential exceptions.
  56. {
  57. int i1 = r1.value(); // Will throw if conversion failed.
  58. int i2 = r2.value(); // Will throw if conversion failed.
  59. }
  60. catch (boost::bad_optional_access const&)
  61. {
  62. // Handle failed conversion.
  63. }
  64. // Exceptions are avoided altogether.
  65. int i1 = r1 ? r1.value() : fallback_value;
  66. int i2 = r2.value_or(fallback_value);
  67. int i3 = convert<int>(str3, cnv).value_or(fallback_value);
  68. int i4 = convert<int>(str3, cnv).value_or_eval(fallback_function);
  69. //]
  70. }
  71. }
  72. //[getting_serious_example5
  73. struct fallback_func
  74. {
  75. int operator()() const { log("Failed to convert"); return 42; }
  76. };
  77. //]
  78. static
  79. void
  80. example4()
  81. {
  82. boost::cnv::cstream cnv;
  83. std::string const str = "123";
  84. int const fallback_value = -1;
  85. //[getting_serious_example4
  86. boost::optional<int> res = boost::convert<int>(str, cnv);
  87. if (!res) log("str conversion failed!");
  88. int i1 = res.value_or(fallback_value);
  89. // ...proceed
  90. //]
  91. //[getting_serious_example6
  92. // Fallback function is called when failed
  93. int i2 = convert<int>(str, cnv).value_or_eval(fallback_func());
  94. int i3 = convert<int>(str, cnv, fallback_func()); // Same as above. Alternative API.
  95. //]
  96. }
  97. static
  98. void
  99. example7()
  100. {
  101. boost::cnv::cstream cnv;
  102. std::string const str = "123";
  103. int const fallback_value = -1;
  104. //[getting_serious_example7
  105. // Error-processing behavior are specified unambiguously and uniformly.
  106. // a) i1: Returns the provided fallback value;
  107. // b) i2: Calls the provided failure-processing function;
  108. // c) i3: Throws an exception.
  109. int i1 = convert<int>(str, cnv, fallback_value);
  110. int i2 = convert<int>(str, cnv, fallback_func());
  111. try
  112. {
  113. // Throwing behavior specified explicitly rather than implied.
  114. int i3 = convert<int>(str, cnv, boost::throw_on_failure);
  115. }
  116. catch (boost::bad_optional_access const&)
  117. {
  118. // Handle failed conversion.
  119. }
  120. //]
  121. //[getting_serious_example8
  122. int m1 = convert<int>(str, cnv).value_or(fallback_value);
  123. int m2 = convert<int>(str, cnv).value_or_eval(fallback_func());
  124. int m3 = convert<int>(str, cnv).value();
  125. //]
  126. //[getting_serious_example9
  127. int n1 = convert<int>(str).value_or(fallback_value);
  128. int n2 = convert<int>(str).value_or_eval(fallback_func());
  129. int n3 = convert<int>(str).value();
  130. //]
  131. }
  132. int
  133. main(int, char const* [])
  134. {
  135. example1();
  136. example4();
  137. example7();
  138. }