123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563 |
- //////////////////////////////////////////////////////////////////////////////
- //
- // (C) Copyright Ion Gaztanaga 2004-2013. Distributed under the Boost
- // Software License, Version 1.0. (See accompanying file
- // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
- //
- // See http://www.boost.org/libs/container for documentation.
- //
- //////////////////////////////////////////////////////////////////////////////
- #ifndef BOOST_CONTAINER_TEST_VECTOR_TEST_HEADER
- #define BOOST_CONTAINER_TEST_VECTOR_TEST_HEADER
- #include <boost/container/detail/config_begin.hpp>
- #include <vector>
- #include <iostream>
- #include <list>
- #include <boost/move/utility_core.hpp>
- #include <boost/container/detail/mpl.hpp>
- #include <boost/move/utility_core.hpp>
- #include <boost/move/iterator.hpp>
- #include <boost/move/make_unique.hpp>
- #include <boost/core/no_exceptions_support.hpp>
- #include <boost/static_assert.hpp>
- #include "print_container.hpp"
- #include "check_equal_containers.hpp"
- #include "movable_int.hpp"
- #include "emplace_test.hpp"
- #include "input_from_forward_iterator.hpp"
- #include "insert_test.hpp"
- #include "container_common_tests.hpp"
- #include <cstddef>
- #include <string>
- #include <vector>
- namespace boost{
- namespace container {
- namespace test{
- template<class Vector>
- struct vector_hash_function_capacity
- {
- typedef typename Vector::size_type size_type;
- template <typename U, size_type (U::*)() const> struct Check;
- template <typename U> static char func(Check<U, &U::capacity> *);
- template <typename U> static int func(...);
- public:
- static const bool value = sizeof(func<Vector>(0)) == sizeof(char);
- };
- template<class V1, class V2>
- bool vector_vector_hash_function_capacity_only(V1&, V2&, boost::container::dtl::false_type)
- {
- return true;
- }
- template<class MyBoostVector, class MyStdVector>
- bool vector_vector_hash_function_capacity_only(MyBoostVector&boostvector, MyStdVector&stdvector, boost::container::dtl::true_type)
- {
- //deque has no reserve
- boostvector.reserve(boostvector.size()*2);
- stdvector.reserve(stdvector.size()*2);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- std::size_t cap = boostvector.capacity();
- boostvector.reserve(cap*2);
- stdvector.reserve(cap*2);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- boostvector.resize(0);
- stdvector.resize(0);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- boostvector.resize(cap*2);
- stdvector.resize(cap*2);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- boostvector.resize(cap*2);
- stdvector.resize(cap*2);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- return true;
- }
- template<class V1, class V2>
- bool vector_copyable_only(V1&, V2&, boost::container::dtl::false_type)
- {
- return true;
- }
- //Function to check if both sets are equal
- template<class MyBoostVector, class MyStdVector>
- bool vector_copyable_only(MyBoostVector &boostvector, MyStdVector &stdvector, boost::container::dtl::true_type)
- {
- typedef typename MyBoostVector::value_type IntType;
- std::size_t size = boostvector.size();
- boostvector.insert(boostvector.end(), 50, IntType(1));
- stdvector.insert(stdvector.end(), 50, 1);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- {
- IntType move_me(1);
- boostvector.insert(boostvector.begin()+size/2, 50, boost::move(move_me));
- stdvector.insert(stdvector.begin()+size/2, 50, 1);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- }
- {
- IntType move_me(2);
- boostvector.assign(boostvector.size()/2, boost::move(move_me));
- stdvector.assign(stdvector.size()/2, 2);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- }
- {
- IntType move_me(3);
- boostvector.assign(boostvector.size()*3-1, boost::move(move_me));
- stdvector.assign(stdvector.size()*3-1, 3);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- }
- {
- IntType copy_me(3);
- const IntType ccopy_me(3);
- boostvector.push_back(copy_me);
- stdvector.push_back(int(3));
- boostvector.push_back(ccopy_me);
- stdvector.push_back(int(3));
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- }
- { //Vector(const Vector &)
- ::boost::movelib::unique_ptr<MyBoostVector> const pv1 =
- ::boost::movelib::make_unique<MyBoostVector>(boostvector);
- ::boost::movelib::unique_ptr<MyStdVector> const pv2 =
- ::boost::movelib::make_unique<MyStdVector>(stdvector);
- MyBoostVector &v1 = *pv1;
- MyStdVector &v2 = *pv2;
- boostvector.clear();
- stdvector.clear();
- boostvector.assign(v1.begin(), v1.end());
- stdvector.assign(v2.begin(), v2.end());
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- }
- { //Vector(const Vector &, alloc)
- ::boost::movelib::unique_ptr<MyBoostVector> const pv1 =
- ::boost::movelib::make_unique<MyBoostVector>(boostvector, typename MyBoostVector::allocator_type());
- ::boost::movelib::unique_ptr<MyStdVector> const pv2 =
- ::boost::movelib::make_unique<MyStdVector>(stdvector);
- MyBoostVector &v1 = *pv1;
- MyStdVector &v2 = *pv2;
- boostvector.clear();
- stdvector.clear();
- boostvector.assign(v1.begin(), v1.end());
- stdvector.assign(v2.begin(), v2.end());
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- }
- { //Vector(n, T)
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp =
- ::boost::movelib::make_unique<MyStdVector>(100, int(5));
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp =
- ::boost::movelib::make_unique<MyBoostVector>(100, IntType(5));
- if(!test::CheckEqualContainers(*boostvectorp, *stdvectorp)) return 1;
- }
- { //Vector(n, T, alloc)
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp =
- ::boost::movelib::make_unique<MyStdVector>(100, int(5));
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp =
- ::boost::movelib::make_unique<MyBoostVector>(100, IntType(5), typename MyBoostVector::allocator_type());
- if(!test::CheckEqualContainers(*boostvectorp, *stdvectorp)) return 1;
- }
- { //Vector(It, It)
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp =
- ::boost::movelib::make_unique<MyStdVector>(100);
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp =
- ::boost::movelib::make_unique<MyBoostVector>(100);
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp2 =
- ::boost::movelib::make_unique<MyBoostVector>(boostvectorp->begin(), boostvectorp->end());
- if(!test::CheckEqualContainers(*boostvectorp2, *stdvectorp)) return 1;
- }
- { //Vector(It, It, alloc)
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp =
- ::boost::movelib::make_unique<MyStdVector>(100);
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp =
- ::boost::movelib::make_unique<MyBoostVector>(100);
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp2 =
- ::boost::movelib::make_unique<MyBoostVector>(boostvectorp->begin(), boostvectorp->end(), typename MyBoostVector::allocator_type());
- if(!test::CheckEqualContainers(*boostvectorp2, *stdvectorp)) return 1;
- }
- { //resize(n, T)
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp =
- ::boost::movelib::make_unique<MyStdVector>();
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp =
- ::boost::movelib::make_unique<MyBoostVector>();
- stdvectorp->resize(100, int(9));
- boostvectorp->resize(100, IntType(9));
- if(!test::CheckEqualContainers(*boostvectorp, *stdvectorp)) return 1;
- }
- //operator=
- {
- //Copy constructor test
- MyBoostVector bcopy((const MyBoostVector&) boostvector);
- MyStdVector scopy((const MyStdVector&) stdvector);
- MyBoostVector bcopy2(boostvector);
- MyStdVector scopy2(stdvector);
- if(!test::CheckEqualContainers(bcopy, scopy)) return false;
- if(!test::CheckEqualContainers(bcopy2, scopy2)) return false;
- //Assignment from a smaller vector
- bcopy2.erase(bcopy2.begin() + bcopy2.size()/2, bcopy2.end());
- scopy2.erase(scopy2.begin() + scopy2.size()/2, scopy2.end());
- bcopy = bcopy2;
- scopy = scopy2;
- if(!test::CheckEqualContainers(bcopy, scopy)) return false;
- //Assignment from a bigger vector with capacity
- bcopy2 = boostvector;
- scopy2 = stdvector;
- if(!test::CheckEqualContainers(bcopy2, scopy2)) return false;
- //Assignment from bigger vector with no capacity
- bcopy2.erase(bcopy2.begin() + bcopy2.size()/2, bcopy2.end());
- scopy2.erase(scopy2.begin() + scopy2.size()/2, scopy2.end());
- bcopy2.shrink_to_fit();
- MyStdVector(scopy2).swap(scopy2);
- bcopy2 = boostvector;
- scopy2 = stdvector;
- if(!test::CheckEqualContainers(bcopy, scopy)) return false;
- //Assignment with equal capacity
- bcopy2 = boostvector;
- scopy2 = stdvector;
- if(!test::CheckEqualContainers(bcopy2, scopy2)) return false;
- }
- return true;
- }
- template<class MyBoostVector>
- int vector_test()
- {
- typedef std::vector<int> MyStdVector;
- typedef typename MyBoostVector::value_type IntType;
- const int max = 100;
- if(!test_range_insertion<MyBoostVector>()){
- return 1;
- }
- { //Vector(n)
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp =
- ::boost::movelib::make_unique<MyBoostVector>(100);
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp =
- ::boost::movelib::make_unique<MyStdVector>(100);
- if(!test::CheckEqualContainers(*boostvectorp, *stdvectorp)) return 1;
- }
- { //Vector(n, alloc)
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp =
- ::boost::movelib::make_unique<MyBoostVector>(100, typename MyBoostVector::allocator_type());
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp =
- ::boost::movelib::make_unique<MyStdVector>(100);
- if(!test::CheckEqualContainers(*boostvectorp, *stdvectorp)) return 1;
- }
- { //Vector(Vector &&)
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp =
- ::boost::movelib::make_unique<MyStdVector>(100);
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp =
- ::boost::movelib::make_unique<MyBoostVector>(100);
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp2 =
- ::boost::movelib::make_unique<MyBoostVector>(::boost::move(*boostvectorp));
- if(!test::CheckEqualContainers(*boostvectorp2, *stdvectorp)) return 1;
- }
- { //Vector(Vector &&, alloc)
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp =
- ::boost::movelib::make_unique<MyStdVector>(100);
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp =
- ::boost::movelib::make_unique<MyBoostVector>(100);
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp2 =
- ::boost::movelib::make_unique<MyBoostVector>
- (::boost::move(*boostvectorp), typename MyBoostVector::allocator_type());
- if(!test::CheckEqualContainers(*boostvectorp2, *stdvectorp)) return 1;
- }
- { //Vector operator=(Vector &&)
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp =
- ::boost::movelib::make_unique<MyStdVector>(100);
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp =
- ::boost::movelib::make_unique<MyBoostVector>(100);
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp2 =
- ::boost::movelib::make_unique<MyBoostVector>();
- *boostvectorp2 = ::boost::move(*boostvectorp);
- if(!test::CheckEqualContainers(*boostvectorp2, *stdvectorp)) return 1;
- }
- {
- ::boost::movelib::unique_ptr<MyBoostVector> const boostvectorp = ::boost::movelib::make_unique<MyBoostVector>();
- ::boost::movelib::unique_ptr<MyStdVector> const stdvectorp = ::boost::movelib::make_unique<MyStdVector>();
- MyBoostVector & boostvector = *boostvectorp;
- MyStdVector & stdvector = *stdvectorp;
- boostvector.resize(100);
- stdvector.resize(100);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- boostvector.resize(200);
- stdvector.resize(200);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- boostvector.resize(0);
- stdvector.resize(0);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- for(int i = 0; i < max; ++i){
- IntType new_int(i);
- boostvector.insert(boostvector.end(), boost::move(new_int));
- stdvector.insert(stdvector.end(), i);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- }
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- typename MyBoostVector::iterator boostit(boostvector.begin());
- typename MyStdVector::iterator stdit(stdvector.begin());
- typename MyBoostVector::const_iterator cboostit = boostit;
- (void)cboostit;
- ++boostit; ++stdit;
- boostvector.erase(boostit);
- stdvector.erase(stdit);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- boostvector.erase(boostvector.begin());
- stdvector.erase(stdvector.begin());
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- {
- //Initialize values
- IntType aux_vect[50];
- for(int i = 0; i < 50; ++i){
- IntType new_int(-1);
- BOOST_STATIC_ASSERT((boost::container::test::is_copyable<boost::container::test::movable_int>::value == false));
- aux_vect[i] = boost::move(new_int);
- }
- int aux_vect2[50];
- for(int i = 0; i < 50; ++i){
- aux_vect2[i] = -1;
- }
- typename MyBoostVector::iterator insert_it =
- boostvector.insert(boostvector.end()
- ,boost::make_move_iterator(&aux_vect[0])
- ,boost::make_move_iterator(aux_vect + 50));
- if(std::size_t(boost::container::iterator_distance(insert_it, boostvector.end())) != 50) return 1;
- stdvector.insert(stdvector.end(), aux_vect2, aux_vect2 + 50);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- for(int i = 0, j = static_cast<int>(boostvector.size()); i < j; ++i){
- boostvector.erase(boostvector.begin());
- stdvector.erase(stdvector.begin());
- }
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- }
- {
- boostvector.resize(100);
- stdvector.resize(100);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- IntType aux_vect[50];
- for(int i = 0; i < 50; ++i){
- IntType new_int(-i);
- aux_vect[i] = boost::move(new_int);
- }
- int aux_vect2[50];
- for(int i = 0; i < 50; ++i){
- aux_vect2[i] = -i;
- }
- typename MyBoostVector::size_type old_size = boostvector.size();
- typename MyBoostVector::iterator insert_it =
- boostvector.insert(boostvector.begin() + old_size/2
- ,boost::make_move_iterator(&aux_vect[0])
- ,boost::make_move_iterator(aux_vect + 50));
- if(boostvector.begin() + old_size/2 != insert_it) return 1;
- stdvector.insert(stdvector.begin() + old_size/2, aux_vect2, aux_vect2 + 50);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- for(int i = 0; i < 50; ++i){
- IntType new_int(-i);
- aux_vect[i] = boost::move(new_int);
- }
- for(int i = 0; i < 50; ++i){
- aux_vect2[i] = -i;
- }
- old_size = boostvector.size();
- //Now try with input iterators instead
- insert_it = boostvector.insert(boostvector.begin() + old_size/2
- ,boost::make_move_iterator(make_input_from_forward_iterator(&aux_vect[0]))
- ,boost::make_move_iterator(make_input_from_forward_iterator(aux_vect + 50))
- );
- if(boostvector.begin() + old_size/2 != insert_it) return 1;
- stdvector.insert(stdvector.begin() + old_size/2, aux_vect2, aux_vect2 + 50);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- }
- boostvector.shrink_to_fit();
- MyStdVector(stdvector).swap(stdvector);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- boostvector.shrink_to_fit();
- MyStdVector(stdvector).swap(stdvector);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- { //push_back with not enough capacity
- IntType push_back_this(1);
- boostvector.push_back(boost::move(push_back_this));
- stdvector.push_back(int(1));
- boostvector.push_back(IntType(1));
- stdvector.push_back(int(1));
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- }
- { //test back()
- const IntType test_this(1);
- if(test_this != boostvector.back()) return 1;
- }
- { //pop_back with enough capacity
- boostvector.pop_back();
- boostvector.pop_back();
- stdvector.pop_back();
- stdvector.pop_back();
- IntType push_back_this(1);
- boostvector.push_back(boost::move(push_back_this));
- stdvector.push_back(int(1));
- boostvector.push_back(IntType(1));
- stdvector.push_back(int(1));
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- }
- if(!vector_copyable_only(boostvector, stdvector
- ,dtl::bool_<boost::container::test::is_copyable<IntType>::value>())){
- return 1;
- }
- boostvector.erase(boostvector.begin());
- stdvector.erase(stdvector.begin());
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- for(int i = 0; i < max; ++i){
- IntType insert_this(i);
- boostvector.insert(boostvector.begin(), boost::move(insert_this));
- stdvector.insert(stdvector.begin(), i);
- boostvector.insert(boostvector.begin(), IntType(i));
- stdvector.insert(stdvector.begin(), int(i));
- }
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- //some comparison operators
- if(!(boostvector == boostvector))
- return 1;
- if(boostvector != boostvector)
- return 1;
- if(boostvector < boostvector)
- return 1;
- if(boostvector > boostvector)
- return 1;
- if(!(boostvector <= boostvector))
- return 1;
- if(!(boostvector >= boostvector))
- return 1;
- //Test insertion from list
- {
- std::list<int> l(50, int(1));
- typename MyBoostVector::iterator it_insert =
- boostvector.insert(boostvector.begin(), l.begin(), l.end());
- if(boostvector.begin() != it_insert) return 1;
- stdvector.insert(stdvector.begin(), l.begin(), l.end());
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- boostvector.assign(l.begin(), l.end());
- stdvector.assign(l.begin(), l.end());
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- boostvector.clear();
- stdvector.clear();
- boostvector.assign(make_input_from_forward_iterator(l.begin()), make_input_from_forward_iterator(l.end()));
- stdvector.assign(l.begin(), l.end());
- if(!test::CheckEqualContainers(boostvector, stdvector)) return 1;
- }
-
- if(!vector_vector_hash_function_capacity_only(boostvector, stdvector, dtl::bool_<vector_hash_function_capacity<MyBoostVector>::value>()))
- return 1;
- boostvector.clear();
- stdvector.clear();
- boostvector.shrink_to_fit();
- MyStdVector(stdvector).swap(stdvector);
- if(!test::CheckEqualContainers(boostvector, stdvector)) return false;
- boostvector.resize(100);
- if(!test_nth_index_of(boostvector))
- return 1;
- }
- std::cout << std::endl << "Test OK!" << std::endl;
- return 0;
- }
- template<typename VectorContainerType>
- bool test_vector_methods_with_initializer_list_as_argument_for()
- {
- #if !defined(BOOST_NO_CXX11_HDR_INITIALIZER_LIST)
- typedef typename VectorContainerType::allocator_type allocator_type;
- {
- const VectorContainerType testedVector = {1, 2, 3};
- const std::vector<int> expectedVector = {1, 2, 3};
- if(!test::CheckEqualContainers(testedVector, expectedVector)) return false;
- }
- {
- const VectorContainerType testedVector( { 1, 2, 3 }, allocator_type() );
- const std::vector<int> expectedVector = {1, 2, 3};
- if(!test::CheckEqualContainers(testedVector, expectedVector)) return false;
- }
- {
- VectorContainerType testedVector = {1, 2, 3};
- testedVector = {11, 12, 13};
- const std::vector<int> expectedVector = {11, 12, 13};
- if(!test::CheckEqualContainers(testedVector, expectedVector)) return false;
- }
- {
- VectorContainerType testedVector = {1, 2, 3};
- testedVector.assign({5, 6, 7});
- const std::vector<int> expectedVector = {5, 6, 7};
- if(!test::CheckEqualContainers(testedVector, expectedVector)) return false;
- }
- {
- VectorContainerType testedVector = {1, 2, 3};
- testedVector.insert(testedVector.cend(), {5, 6, 7});
- const std::vector<int> expectedVector = {1, 2, 3, 5, 6, 7};
- if(!test::CheckEqualContainers(testedVector, expectedVector)) return false;
- }
- return true;
- #else
- return true;
- #endif
- }
- } //namespace test{
- } //namespace container {
- } //namespace boost{
- #include <boost/container/detail/config_end.hpp>
- #endif //BOOST_CONTAINER_TEST_VECTOR_TEST_HEADER
|