]>
Commit | Line | Data |
---|---|---|
7c673cae FG |
1 | // Boost.Assign library |
2 | // | |
3 | // Copyright Thorsten Ottosen 2003-2004. Use, modification and | |
4 | // distribution is subject to the Boost Software License, Version | |
5 | // 1.0. (See accompanying file LICENSE_1_0.txt or copy at | |
6 | // http://www.boost.org/LICENSE_1_0.txt) | |
7 | // | |
8 | // For more information, see http://www.boost.org/libs/assign/ | |
9 | // | |
10 | ||
11 | ||
12 | #include <boost/detail/workaround.hpp> | |
13 | ||
20effc67 | 14 | #if BOOST_WORKAROUND(BOOST_BORLANDC, BOOST_TESTED_AT(0x564)) |
b32b8144 | 15 | # pragma warn -8091 // suppress warning in Boost.Test |
7c673cae FG |
16 | # pragma warn -8057 // unused argument argc/argv in Boost.Test |
17 | #endif | |
18 | ||
19 | #include <boost/assign/list_of.hpp> | |
20 | #include <boost/test/test_tools.hpp> | |
21 | #include <boost/array.hpp> | |
22 | #include <algorithm> | |
23 | #include <vector> | |
24 | #include <list> | |
25 | #include <deque> | |
26 | #include <set> | |
27 | #include <map> | |
28 | #include <stack> | |
29 | #include <string> | |
30 | #include <cstdlib> | |
31 | #include <complex> | |
32 | ||
33 | struct nothing | |
34 | { | |
35 | template< class T > | |
36 | void operator()( T ) | |
37 | { } | |
38 | ||
39 | }; | |
40 | ||
41 | template< class Range > | |
42 | void for_each( const Range& r ) | |
43 | { | |
44 | std::for_each( r.begin(), r.end(), nothing() ); | |
45 | } | |
46 | ||
47 | namespace ba = boost::assign; | |
48 | ||
49 | template< class C > | |
50 | void test_sequence_list_of_string() | |
51 | { | |
52 | #if BOOST_WORKAROUND(BOOST_MSVC, <=1300) | |
53 | const C c = ba::list_of( "foo" )( "bar" ).to_container( c ); | |
54 | #else | |
55 | const C c = ba::list_of( "foo" )( "bar" ); | |
56 | #endif | |
57 | BOOST_CHECK_EQUAL( c.size(), 2u ); | |
58 | } | |
59 | ||
60 | struct parameter_list | |
61 | { | |
62 | int val; | |
63 | ||
64 | template< class T > | |
65 | parameter_list( T ) | |
66 | : val(0) | |
67 | { } | |
68 | ||
69 | template< class T > | |
70 | parameter_list( const T&, int ) | |
71 | : val(1) | |
72 | { } | |
73 | }; | |
74 | ||
75 | template< class C > | |
76 | void test_sequence_list_of_int() | |
77 | { | |
78 | using namespace std; | |
79 | #if BOOST_WORKAROUND(BOOST_MSVC, <=1300) | |
80 | ||
81 | const C c = ba::list_of<int>(1)(2)(3)(4).to_container( c ); | |
82 | const C c2 = ba::list_of(1)(2)(3)(4).to_container( c2 ); | |
83 | BOOST_CHECK_EQUAL( c.size(), 4u ); | |
84 | BOOST_CHECK_EQUAL( c2.size(), 4u ); | |
85 | C c3 = ba::list_of(1).repeat( 1, 2 )(3).to_container( c3 ); | |
86 | BOOST_CHECK_EQUAL( c3.size(), 3u ); | |
87 | ||
88 | c3 = ba::list_of(1).repeat_fun( 10, &rand )(2)(3).to_container( c3 ); | |
89 | BOOST_CHECK_EQUAL( c3.size(), 13u ); | |
90 | ||
91 | #else | |
92 | ||
93 | const C c = ba::list_of<int>(1)(2)(3)(4); | |
94 | const C c2 = ba::list_of(1)(2)(3)(4); | |
95 | BOOST_CHECK_EQUAL( c.size(), 4u ); | |
96 | BOOST_CHECK_EQUAL( c2.size(), 4u ); | |
97 | C c3 = ba::list_of(1).repeat( 1, 2 )(3); | |
98 | BOOST_CHECK_EQUAL( c3.size(), 3u ); | |
99 | ||
20effc67 | 100 | #if BOOST_WORKAROUND(BOOST_BORLANDC, BOOST_TESTED_AT(0x564)) |
7c673cae FG |
101 | // BCB fails to use operator=() directly, |
102 | // it must be worked around using e.g. auxiliary variable | |
103 | C aux = ba::list_of(1).repeat_fun( 10, &rand )(2)(3); | |
104 | BOOST_CHECK_EQUAL( aux.size(), 13u ); | |
105 | c3 = aux; | |
106 | BOOST_CHECK_EQUAL( c3.size(), 13u ); | |
11fdf7f2 | 107 | #elif defined( BOOST_NO_CXX11_HDR_INITIALIZER_LIST ) |
7c673cae FG |
108 | c3 = ba::list_of(1).repeat_fun( 10, &rand )(2)(3); |
109 | BOOST_CHECK_EQUAL( c3.size(), 13u ); | |
110 | #endif | |
111 | ||
92f5a8d4 TL |
112 | #if !defined( BOOST_NO_CXX11_FUNCTION_TEMPLATE_DEFAULT_ARGS ) |
113 | C c4; | |
114 | c4 = ba::list_of(1)(2)(3)(4); | |
115 | BOOST_CHECK_EQUAL( c4.size(), 4u ); | |
116 | C c5(ba::list_of(1)(2)(3)(4)(5)); | |
117 | BOOST_CHECK_EQUAL( c5.size(), 5u ); | |
118 | #endif | |
119 | ||
7c673cae FG |
120 | #endif |
121 | ||
122 | parameter_list p( ba::list_of(1)(2), 3u ); | |
123 | BOOST_CHECK_EQUAL( p.val, 1 ); | |
124 | ||
125 | } | |
126 | ||
127 | template< class C > | |
128 | void test_map_list_of() | |
129 | { | |
130 | const C c = ba::list_of< std::pair<std::string,int> >( "foo", 1 )( "bar", 2 )( "buh", 3 )( "bah", 4 ); | |
131 | BOOST_CHECK_EQUAL( c.size(), 4u ); | |
132 | const C c2 = ba::map_list_of( "foo", 1 )( "bar", 2 )( "buh", 3 )( "bah", 4 ); | |
133 | BOOST_CHECK_EQUAL( c2.size(), 4u ); | |
134 | } | |
135 | ||
136 | void test_vector_matrix() | |
137 | { | |
138 | using namespace boost; | |
139 | using namespace boost::assign; | |
140 | using namespace std; | |
141 | using boost::array; | |
142 | ||
143 | #if BOOST_WORKAROUND(BOOST_DINKUMWARE_STDLIB, == 1) || BOOST_WORKAROUND(BOOST_MSVC, <=1300) | |
144 | #else | |
145 | ||
146 | const int sz = 3; | |
147 | typedef array<int,sz> row3; | |
148 | typedef array<row3,sz> matrix3x3; | |
149 | ||
150 | ||
151 | matrix3x3 m = list_of( list_of(1)(2)(3) ) | |
152 | ( list_of(4)(5)(6) ) | |
153 | ( list_of(7)(8)(9) ); | |
154 | ||
155 | for( int i = 0; i != sz; ++i ) | |
156 | for( int j = 0; j != sz; ++j ) | |
157 | BOOST_CHECK_EQUAL( m[i][j], i*sz + j + 1 ); | |
158 | ||
159 | typedef vector<int> row; | |
160 | typedef vector<row> matrix; | |
161 | ||
162 | // | |
163 | // note: some libraries need a little help | |
164 | // with the conversion, hence the 'row' template parameter. | |
165 | // | |
166 | matrix m2 = list_of< row >( list_of(1)(2)(3) ) | |
167 | ( list_of(4)(5) ) | |
168 | ( list_of(6) ); | |
169 | ||
170 | for( int i = 0; i != sz; ++i ) | |
171 | for( int j = 0; j != sz - i; ++j ) | |
172 | BOOST_CHECK_EQUAL( m[i][j], i*sz + j + 1 ); | |
173 | ||
174 | #endif | |
175 | ||
176 | } | |
177 | ||
178 | void test_map_list_of() | |
179 | { | |
180 | /* | |
181 | maybe in the future... | |
182 | ||
183 | using namespace std; | |
184 | using namespace boost::assign; | |
185 | ||
186 | typedef vector<int> score_type; | |
187 | typedef map<string,score_type> team_score_map; | |
188 | ||
189 | team_score_map team_score = map_list_of | |
190 | ( "Team Foo", list_of(1)(1)(0) ) | |
191 | ( "Team Bar", list_of(0)(0)(0) ) | |
192 | ( "Team FooBar", list_of(0)(0)(1) ); | |
193 | BOOST_CHECK_EQUAL( team_score.size(), 3 ); | |
194 | BOOST_CHECK_EQUAL( team_score[ "Team Foo" ][1], 1 ); | |
195 | BOOST_CHECK_EQUAL( team_score[ "Team Bar" ][0], 0 ); | |
196 | */ | |
197 | ||
198 | } | |
199 | ||
200 | /* | |
201 | void test_complex_list_of() | |
202 | { | |
203 | typedef std::complex<float> complex_t; | |
204 | std::vector<complex_t> v; | |
205 | v = ba::list_of<complex_t>(1,2)(2,3)(4,5)(0). | |
206 | repeat_from_to( complex_t(0,0), complex_t(10,10), complex_t(1,1) ); | |
207 | } | |
208 | */ | |
209 | ||
210 | struct five | |
211 | { | |
212 | five( int, int, int, int, int ) | |
213 | { | |
214 | } | |
215 | }; | |
216 | ||
217 | void test_list_of() | |
218 | { | |
219 | ba::list_of< five >(1,2,3,4,5)(6,7,8,9,10); | |
220 | ||
92f5a8d4 | 221 | /* Maybe this could be useful in a later version? |
7c673cae FG |
222 | |
223 | // an anonymous lists, fulfills Range concept | |
224 | for_each( ba::list_of( T() )( T() )( T() ) ); | |
225 | ||
226 | // non-anonymous lists | |
227 | ba::generic_list<T> list_1 = ba::list_of( T() ); | |
228 | BOOST_CHECK_EQUAL( list_1.size(), 1 ); | |
229 | ba::generic_list<T> list_2 = list_1 + ba::list_of( T() )( T() ) + list_1; | |
230 | BOOST_CHECK_EQUAL( list_2.size(), 4 ); | |
231 | list_1 += list_2; | |
232 | BOOST_CHECK_EQUAL( list_1.size(), 5 ); | |
233 | */ | |
234 | } | |
235 | ||
236 | // | |
92f5a8d4 | 237 | // @remark: ADL is required here, but it is a bit weird to |
7c673cae FG |
238 | // open up namespace std. Perhaps Boost.Test needs a |
239 | // better configuration option. | |
240 | // | |
241 | namespace std | |
242 | { | |
243 | template< class T, class Elem, class Traits > | |
244 | inline std::basic_ostream<Elem,Traits>& | |
245 | operator<<( std::basic_ostream<Elem, Traits>& Os, | |
246 | const std::vector<T>& r ) | |
247 | { | |
248 | return Os << ::boost::make_iterator_range( r.begin(), r.end() ); | |
249 | } | |
250 | } | |
251 | ||
252 | template <class Seq> | |
253 | inline std::vector<int> as_seq( const Seq& s ) | |
254 | { | |
255 | std::vector<int> c; | |
256 | return s.to_container( c ); | |
257 | } | |
258 | ||
259 | void test_comparison_operations() | |
260 | { | |
261 | BOOST_CHECK_EQUAL( ba::list_of(0)(1)(2), as_seq(ba::list_of(0)(1)(2)) ); | |
262 | BOOST_CHECK_NE( ba::list_of(0)(1)(2), as_seq(ba::list_of(-1)(1)(2)) ); | |
263 | BOOST_CHECK_LT( ba::list_of(0)(1)(2), as_seq(ba::list_of(0)(1)(3)) ); | |
264 | BOOST_CHECK_LE( ba::list_of(0)(1)(2), as_seq(ba::list_of(0)(1)(2)) ); | |
265 | BOOST_CHECK_GT( ba::list_of(0)(1)(3), as_seq(ba::list_of(0)(1)(2)) ); | |
266 | BOOST_CHECK_GE( ba::list_of(0)(1)(2), as_seq(ba::list_of(0)(1)(2)) ); | |
267 | BOOST_CHECK_EQUAL( as_seq(ba::list_of(0)(1)(2)), ba::list_of(0)(1)(2) ); | |
268 | BOOST_CHECK_NE( as_seq(ba::list_of(0)(1)(2)), ba::list_of(-1)(1)(2) ); | |
269 | BOOST_CHECK_LT( as_seq(ba::list_of(0)(1)(2)), ba::list_of(0)(1)(3) ); | |
270 | BOOST_CHECK_LE( as_seq(ba::list_of(0)(1)(2)), ba::list_of(0)(1)(2) ); | |
271 | BOOST_CHECK_GT( as_seq(ba::list_of(0)(1)(3)), ba::list_of(0)(1)(2) ); | |
272 | BOOST_CHECK_GE( as_seq(ba::list_of(0)(1)(2)), ba::list_of(0)(1)(2) ); | |
273 | } | |
274 | ||
275 | void check_list_of() | |
276 | { | |
277 | test_sequence_list_of_int< std::vector<int> >(); | |
278 | test_sequence_list_of_int< std::list<int> >(); | |
279 | test_sequence_list_of_int< std::deque<int> >(); | |
280 | test_sequence_list_of_int< std::set<int> >(); | |
281 | test_sequence_list_of_int< std::multiset<int> >(); | |
282 | test_sequence_list_of_int< std::vector<float> >(); | |
283 | ||
284 | test_sequence_list_of_string< std::vector<std::string> >(); | |
285 | ||
286 | test_map_list_of< std::map<std::string,int> >(); | |
287 | test_map_list_of< std::multimap<std::string,int> >(); | |
288 | ||
289 | std::stack<std::string> s = ba::list_of( "Foo" )( "Bar" )( "FooBar" ).to_adapter( s ); | |
290 | test_list_of(); | |
291 | test_vector_matrix(); | |
292 | test_comparison_operations(); | |
293 | } | |
294 | ||
295 | ||
296 | ||
297 | #include <boost/test/unit_test.hpp> | |
298 | using boost::unit_test::test_suite; | |
299 | ||
300 | test_suite* init_unit_test_suite( int argc, char* argv[] ) | |
301 | { | |
302 | test_suite* test = BOOST_TEST_SUITE( "List Test Suite" ); | |
303 | ||
304 | test->add( BOOST_TEST_CASE( &check_list_of ) ); | |
305 | ||
306 | return test; | |
307 | } | |
308 | ||
309 |