1 //-----------------------------------------------------------------------------
2 // boost-libs variant/test/test8.cpp header file
3 // See http://www.boost.org for updates, documentation, and revision history.
4 //-----------------------------------------------------------------------------
5 //
6 // Copyright (c) 2003
7 // Eric Friedman, Itay Maman
8 //
9 // Distributed under the Boost Software License, Version 1.0. (See
10 // accompanying file LICENSE_1_0.txt or copy at
11 // http://www.boost.org/LICENSE_1_0.txt)
12
13 #include "boost/core/lightweight_test.hpp"
14 #include "boost/variant.hpp"
15
16 #include <iostream>
17 #include <vector>
18 #include <string>
19
20 using namespace boost;
21
22 typedef variant<float, std::string, int, std::vector<std::string> > t_var1;
23
24 struct int_sum : static_visitor<>
25 {
int_sumint_sum26 int_sum() : result_(0) { }
27
operator ()int_sum28 void operator()(int t)
29 {
30 result_ += t;
31 }
32
operator ()int_sum33 result_type operator()(float ) { }
operator ()int_sum34 result_type operator()(const std::string& ) { }
operator ()int_sum35 result_type operator()(const std::vector<std::string>& ) { }
36
37 int result_;
38 };
39
40 template <typename T, typename Variant>
check_pass(Variant & v,T value)41 T& check_pass(Variant& v, T value)
42 {
43 BOOST_TEST(get<T>(&v));
44
45 try
46 {
47 T& r = get<T>(v);
48 BOOST_TEST(r == value);
49 return r;
50 }
51 catch(boost::bad_get&)
52 {
53 throw; // must never reach
54 }
55 }
56
57 template <typename T, typename Variant>
check_fail(Variant & v)58 void check_fail(Variant& v)
59 {
60 BOOST_TEST(!relaxed_get<T>(&v));
61
62 try
63 {
64 T& r = relaxed_get<T>(v);
65 (void)r; // suppress warning about r not being used
66 BOOST_TEST(false && relaxed_get<T>(&v)); // should never reach
67 }
68 catch(const boost::bad_get& e)
69 {
70 BOOST_TEST(!!e.what()); // make sure that what() is const qualified and returnes something
71 }
72 }
73
main()74 int main()
75 {
76 int_sum acc;
77 t_var1 v1 = 800;
78
79 // check get on non-const variant
80 {
81 int& r1 = check_pass<int>(v1, 800);
82 const int& cr1 = check_pass<const int>(v1, 800);
83
84 check_fail<float>(v1);
85 check_fail<const float>(v1);
86 check_fail<short>(v1);
87 check_fail<const short>(v1);
88
89 apply_visitor(acc, v1);
90 BOOST_TEST(acc.result_ == 800);
91
92 r1 = 920; // NOTE: modifies content of v1
93 apply_visitor(acc, v1);
94 BOOST_TEST(cr1 == 920);
95 BOOST_TEST(acc.result_ == 800 + 920);
96 }
97
98 // check const correctness:
99 {
100 const t_var1& c = v1;
101
102 check_pass<const int>(c, 920);
103
104 //check_fail<int>(c);
105 check_fail<const float>(c);
106 //check_fail<float>(c);
107 check_fail<const short>(c);
108 //check_fail<short>(c);
109 }
110
111 return boost::report_errors();
112 }
113
114