• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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/min_element.hpp>
10 
11 #include <boost/test/test_tools.hpp>
12 #include <boost/test/unit_test.hpp>
13 
14 #include <boost/assign.hpp>
15 #include <boost/range/iterator.hpp>
16 #include "../test_driver/range_return_test_driver.hpp"
17 #include <algorithm>
18 #include <functional>
19 #include <list>
20 #include <numeric>
21 #include <deque>
22 #include <vector>
23 
24 namespace boost_range_test_algorithm_min_element
25 {
26     class min_element_test_policy
27     {
28     public:
29         template< class Container >
30         BOOST_DEDUCED_TYPENAME boost::range_iterator<Container>::type
test_iter(Container & cont)31         test_iter(Container& cont)
32         {
33             typedef BOOST_DEDUCED_TYPENAME boost::range_iterator<Container>::type iter_t;
34             iter_t result = boost::min_element(cont);
35             BOOST_CHECK( result == boost::min_element(boost::make_iterator_range(cont)) );
36             return result;
37         }
38 
39         template< boost::range_return_value return_type >
40         struct test_range
41         {
42             template< class Container, class Policy >
43             BOOST_DEDUCED_TYPENAME boost::range_return<Container,return_type>::type
operator ()boost_range_test_algorithm_min_element::min_element_test_policy::test_range44             operator()(Policy&, Container& cont)
45             {
46                 typedef BOOST_DEDUCED_TYPENAME boost::range_return<Container,return_type>::type result_t;
47                 result_t result = boost::min_element<return_type>(cont);
48                 BOOST_CHECK( result == boost::min_element<return_type>(boost::make_iterator_range(cont)) );
49                 return result;
50             }
51         };
52 
53         template< class Container >
54         BOOST_DEDUCED_TYPENAME boost::range_iterator<Container>::type
reference(Container & cont)55         reference(Container& cont)
56         {
57             return std::min_element(cont.begin(), cont.end());
58         }
59     };
60 
61     template<class Pred>
62     class min_element_pred_test_policy
63     {
64     public:
65         template< class Container >
66         BOOST_DEDUCED_TYPENAME boost::range_iterator<Container>::type
test_iter(Container & cont)67         test_iter(Container& cont)
68         {
69             typedef BOOST_DEDUCED_TYPENAME boost::range_iterator<Container>::type iter_t;
70             iter_t result = boost::min_element(cont, Pred());
71             BOOST_CHECK( result == boost::min_element(
72                                     boost::make_iterator_range(cont), Pred()) );
73             return result;
74         }
75 
pred() const76         Pred pred() const { return Pred(); }
77 
78         template< boost::range_return_value return_type >
79         struct test_range
80         {
81             template< class Container, class Policy >
82             BOOST_DEDUCED_TYPENAME boost::range_return<Container,return_type>::type
operator ()boost_range_test_algorithm_min_element::min_element_pred_test_policy::test_range83             operator()(Policy& policy, Container& cont)
84             {
85                 typedef BOOST_DEDUCED_TYPENAME boost::range_return<Container,return_type>::type result_t;
86                 result_t result = boost::min_element<return_type>(cont, policy.pred());
87                 BOOST_CHECK( result == boost::min_element<return_type>(
88                                 boost::make_iterator_range(cont), policy.pred()) );
89                 return result;
90             }
91         };
92 
93         template< class Container >
94         BOOST_DEDUCED_TYPENAME boost::range_iterator<Container>::type
reference(Container & cont)95         reference(Container& cont)
96         {
97             return std::min_element(cont.begin(), cont.end(), Pred());
98         }
99     };
100 
101     template<class Container, class TestPolicy>
test_min_element_impl(TestPolicy policy)102     void test_min_element_impl(TestPolicy policy)
103     {
104         using namespace boost::assign;
105 
106         typedef BOOST_DEDUCED_TYPENAME Container::value_type
107                                                 value_t BOOST_RANGE_UNUSED;
108 
109         typedef BOOST_DEDUCED_TYPENAME boost::remove_const<Container>::type
110                                                 container_t;
111 
112         boost::range_test::range_return_test_driver test_driver;
113 
114         container_t cont;
115 
116         test_driver(cont, policy);
117 
118         cont.clear();
119         cont += 1;
120 
121         test_driver(cont, policy);
122 
123         cont.clear();
124         cont += 1,2,2,2,3,4,5,6,7,8,9;
125 
126         test_driver(cont, policy);
127     }
128 
129     template<class Container>
test_min_element_impl()130     void test_min_element_impl()
131     {
132         test_min_element_impl<Container>(min_element_test_policy());
133 
134         test_min_element_impl<Container>(
135             min_element_pred_test_policy<std::less<int> >());
136 
137         test_min_element_impl<Container>(
138             min_element_pred_test_policy<std::greater<int> >());
139     }
140 
test_min_element()141     void test_min_element()
142     {
143         test_min_element_impl< const std::vector<int> >();
144         test_min_element_impl< const std::deque<int> >();
145         test_min_element_impl< const std::list<int> >();
146 
147         test_min_element_impl< std::vector<int> >();
148         test_min_element_impl< std::deque<int> >();
149         test_min_element_impl< std::list<int> >();
150     }
151 }
152 
153 boost::unit_test::test_suite*
init_unit_test_suite(int argc,char * argv[])154 init_unit_test_suite(int argc, char* argv[])
155 {
156     boost::unit_test::test_suite* test
157         = BOOST_TEST_SUITE( "RangeTestSuite.algorithm.min_element" );
158 
159     test->add( BOOST_TEST_CASE( &boost_range_test_algorithm_min_element::test_min_element ) );
160 
161     return test;
162 }
163