1// Copyright Neil Groves 2009. Use, modification and
2// distribution is subject to the Boost Software License, Version
3// 1.0. (See accompanying file LICENSE_1_0.txt or copy at
4// http://www.boost.org/LICENSE_1_0.txt)
5//
6//
7// For more information, see http://www.boost.org/libs/range/
8//
9#include <boost/range/algorithm/set_algorithm.hpp>
10
11#include <boost/test/test_tools.hpp>
12#include <boost/test/unit_test.hpp>
13
14#include <boost/assign.hpp>
15#include <algorithm>
16#include <functional>
17#include <list>
18#include <numeric>
19#include <deque>
20#include <vector>
21
22namespace boost
23{
24 namespace
25 {
26 template<class Container1, class Iterator, class Container2>
27 void check_result(
28 Container1& reference,
29 Iterator reference_result,
30 Container2& test_cont,
31 Iterator test_result
32 )
33 {
34 BOOST_CHECK_EQUAL(
35 std::distance<Iterator>(reference.begin(), reference_result),
36 std::distance<Iterator>(test_cont.begin(), test_result)
37 );
38
39 BOOST_CHECK_EQUAL_COLLECTIONS(
40 reference.begin(), reference.end(),
41 test_cont.begin(), test_cont.end()
42 );
43 }
44
45 template<class Container1, class Container2>
46 void test(Container1& cont1, Container2& cont2)
47 {
48 typedef BOOST_DEDUCED_TYPENAME Container1::value_type value_t;
49 typedef BOOST_DEDUCED_TYPENAME std::vector<value_t>::iterator iterator_t;
50
51 std::vector<value_t> reference(cont1.size() + cont2.size());
52 std::vector<value_t> test_cont(reference);
53
54 iterator_t reference_result
55 = std::set_union(cont1.begin(), cont1.end(),
56 cont2.begin(), cont2.end(),
57 reference.begin());
58
59 iterator_t test_result
60 = boost::set_union(cont1, cont2, test_cont.begin());
61
62 check_result(reference, reference_result,
63 test_cont, test_result);
64
65 test_result = boost::set_union(boost::make_iterator_range(cont1),
66 cont2, test_cont.begin());
67
68 check_result(reference, reference_result,
69 test_cont, test_result);
70
71 test_result = boost::set_union(cont1,
72 boost::make_iterator_range(cont2),
73 test_cont.begin());
74
75 check_result(reference, reference_result,
76 test_cont, test_result);
77
78 test_result = boost::set_union(boost::make_iterator_range(cont1),
79 boost::make_iterator_range(cont2),
80 test_cont.begin());
81
82 check_result(reference, reference_result,
83 test_cont, test_result);
84 }
85
86 template<class Container, class BinaryPredicate>
87 void sort_container(Container& cont, BinaryPredicate pred)
88 {
89 typedef BOOST_DEDUCED_TYPENAME Container::value_type value_t;
90
91 std::vector<value_t> temp(cont.begin(), cont.end());
92 std::sort(temp.begin(), temp.end(), pred);
93 cont.assign(temp.begin(), temp.end());
94 }
95
96 template<class Container1,
97 class Container2,
98 class BinaryPredicate>
99 void test_pred(Container1 cont1, Container2 cont2,
100 BinaryPredicate pred)
101 {
102 typedef BOOST_DEDUCED_TYPENAME Container1::value_type value_t;
103 typedef BOOST_DEDUCED_TYPENAME std::vector<value_t>::iterator iterator_t;
104
105 sort_container(cont1, pred);
106 sort_container(cont2, pred);
107
108 std::vector<value_t> reference(cont1.size() + cont2.size());
109 std::vector<value_t> test_cont(reference);
110
111 iterator_t reference_result
112 = std::set_union(cont1.begin(), cont1.end(),
113 cont2.begin(), cont2.end(),
114 reference.begin(),
115 pred);
116
117 iterator_t test_result
118 = boost::set_union(cont1, cont2, test_cont.begin(), pred);
119
120 check_result(reference, reference_result,
121 test_cont, test_result);
122
123 test_result = boost::set_union(boost::make_iterator_range(cont1),
124 cont2, test_cont.begin(), pred);
125
126 check_result(reference, reference_result,
127 test_cont, test_result);
128
129 test_result = boost::set_union(cont1,
130 boost::make_iterator_range(cont2),
131 test_cont.begin(), pred);
132
133 check_result(reference, reference_result,
134 test_cont, test_result);
135
136 test_result = boost::set_union(boost::make_iterator_range(cont1),
137 boost::make_iterator_range(cont2),
138 test_cont.begin(), pred);
139
140 check_result(reference, reference_result,
141 test_cont, test_result);
142 }
143
144 template<class Container1, class Container2>
145 void test_set_union_impl(
146 Container1& cont1,
147 Container2& cont2
148 )
149 {
150 test(cont1, cont2);
151 test_pred(cont1, cont2, std::less<int>());
152 test_pred(cont1, cont2, std::greater<int>());
153 }
154
155 template<class Container1, class Container2>
156 void test_set_union_impl()
157 {
158 using namespace boost::assign;
159
160 Container1 cont1;
161 Container2 cont2;
162
163 test_set_union_impl(cont1, cont2);
164
165 cont1.clear();
166 cont2.clear();
167 cont1 += 1;
168 test_set_union_impl(cont1, cont2);
169
170 cont1.clear();
171 cont2.clear();
172 cont2 += 1;
173 test_set_union_impl(cont1, cont2);
174
175 cont1.clear();
176 cont2.clear();
177 cont1 += 1,2,3,4,5,6,7,8,9;
178 cont2 += 2,3,4;
179 test_set_union_impl(cont1, cont2);
180
181 cont1.clear();
182 cont2.clear();
183 cont1 += 2,3,4;
184 cont2 += 1,2,3,4,5,6,7,8,9;
185 test_set_union_impl(cont1, cont2);
186 }
187
188 void test_set_union()
189 {
190 test_set_union_impl< std::vector<int>, std::vector<int> >();
191 test_set_union_impl< std::list<int>, std::list<int> >();
192 test_set_union_impl< std::deque<int>, std::deque<int> >();
193 test_set_union_impl< std::vector<int>, std::list<int> >();
194 test_set_union_impl< std::list<int>, std::vector<int> >();
195 }
196 }
197}
198
199
200boost::unit_test::test_suite*
201init_unit_test_suite(int argc, char* argv[])
202{
203 boost::unit_test::test_suite* test
204 = BOOST_TEST_SUITE( "RangeTestSuite.algorithm.set_union" );
205
206 test->add( BOOST_TEST_CASE( &boost::test_set_union ) );
207
208 return test;
209}
210

source code of boost/libs/range/test/algorithm_test/set_union.cpp