1 // Boost.Range library
2 //
3 // Copyright Neil Groves 2009. 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 //
9 // For more information, see http://www.boost.org/libs/range/
10 //
11 #include <boost/range/adaptor/uniqued.hpp>
12 #include <boost/range/adaptor/transformed.hpp>
13 #include <boost/range/algorithm/unique_copy.hpp>
14 #include <boost/range/algorithm_ext/push_back.hpp>
15 #include <boost/algorithm/string/predicate.hpp>
16
17 #include <boost/test/test_tools.hpp>
18 #include <boost/test/unit_test.hpp>
19
20 #include <boost/assign.hpp>
21 #include <boost/range/algorithm_ext.hpp>
22
23 #include <algorithm>
24 #include <list>
25 #include <set>
26 #include <vector>
27
28 namespace boost
29 {
30 namespace
31 {
32 template< class Container >
uniqued_test_impl(Container & c)33 void uniqued_test_impl( Container& c )
34 {
35 using namespace boost::adaptors;
36
37 std::vector< int > test_result1;
38 boost::push_back(test_result1, c | uniqued);
39
40 std::vector< int > test_result2;
41 boost::push_back(test_result2, adaptors::unique(c));
42
43 std::vector< int > reference(c.begin(), c.end());
44 reference.erase(
45 std::unique(reference.begin(), reference.end()),
46 reference.end());
47
48 BOOST_CHECK_EQUAL_COLLECTIONS( reference.begin(), reference.end(),
49 test_result1.begin(), test_result1.end() );
50
51 BOOST_CHECK_EQUAL_COLLECTIONS( reference.begin(), reference.end(),
52 test_result2.begin(), test_result2.end() );
53 }
54
55 template< class Container >
uniqued_test_impl()56 void uniqued_test_impl()
57 {
58 using namespace boost::assign;
59
60 Container c;
61
62 // Test empty
63 uniqued_test_impl(c);
64
65 // Test one
66 c += 1;
67 uniqued_test_impl(c);
68
69 // Test many
70 c += 1,1,1,2,2,2,2,2,3,3,3,3,4,5,6,6,6,7,7,7,8,8,9,9,9,9,9,10;
71 uniqued_test_impl(c);
72 }
73
uniqued_test()74 void uniqued_test()
75 {
76 uniqued_test_impl< std::vector< int > >();
77 uniqued_test_impl< std::list< int > >();
78 uniqued_test_impl< std::set< int > >();
79 uniqued_test_impl< std::multiset< int > >();
80 }
81
82 class istring
83 {
84 public:
istring()85 istring()
86 : m_value("")
87 {
88 }
89
istring(const char * value)90 explicit istring(const char* value)
91 : m_value(value)
92 {
93 }
94
operator ==(istring r) const95 bool operator==(istring r) const
96 {
97 return boost::iequals(m_value, r.m_value);
98 }
99
operator !=(istring r) const100 bool operator!=(istring r) const
101 {
102 return !operator==(r);
103 }
104
operator <<(std::ostream & out,istring o)105 inline friend std::ostream& operator<<(std::ostream& out, istring o)
106 {
107 return out << o.m_value;
108 }
109
get() const110 const char* get() const { return m_value; }
111
112 private:
113 const char* m_value;
114 };
115
116 struct istring_to_string
117 {
118 typedef std::string result_type;
119
operator ()boost::__anon4f4e6bb40111::istring_to_string120 std::string operator()(istring s) const
121 {
122 return s.get();
123 }
124 };
125
126 // This is based on a test-case provided by Eric Neibler.
uniqued_return_first()127 void uniqued_return_first()
128 {
129 using namespace boost::adaptors;
130
131 std::vector<istring> strs;
132 strs.push_back(istring("hello"));
133 strs.push_back(istring("hElLo"));
134 strs.push_back(istring("HELLO"));
135 strs.push_back(istring("ZZZZ"));
136
137 std::vector<istring> output1;
138
139 boost::unique_copy(strs, std::back_inserter(output1));
140
141 std::vector<istring> output2;
142 boost::push_back(output2, strs | uniqued);
143
144 std::vector<std::string> test1;
145 boost::push_back(test1, output1 | transformed(istring_to_string()));
146
147 std::vector<std::string> test2;
148 boost::push_back(test2, output2 | transformed(istring_to_string()));
149
150 BOOST_CHECK_EQUAL_COLLECTIONS(test1.begin(), test1.end(),
151 test2.begin(), test2.end());
152 }
153
154 } // anonymous namespace
155 } // namespace boost
156
157 boost::unit_test::test_suite*
init_unit_test_suite(int argc,char * argv[])158 init_unit_test_suite(int argc, char* argv[])
159 {
160 boost::unit_test::test_suite* test
161 = BOOST_TEST_SUITE( "RangeTestSuite.adaptor.uniqued" );
162
163 test->add( BOOST_TEST_CASE( &boost::uniqued_test ) );
164
165 test->add(BOOST_TEST_CASE(&boost::uniqued_return_first));
166
167 return test;
168 }
169