From 704da86b1b53e287e63e3053c5521aaf9178e0ce Mon Sep 17 00:00:00 2001 From: cyborg1811m Date: Sat, 6 Jan 2024 18:11:11 +0100 Subject: [PATCH] added second copy constructor, tests for copy and move constructors and bugfixed copy and move constructors --- include/const_vector.hpp | 34 +++++--- test/test_main.cpp | 178 +++++++++++++++++++++++++++++++++++++-- 2 files changed, 191 insertions(+), 21 deletions(-) diff --git a/include/const_vector.hpp b/include/const_vector.hpp index 88f55d8..102db22 100644 --- a/include/const_vector.hpp +++ b/include/const_vector.hpp @@ -33,8 +33,8 @@ namespace cc { using const_reverse_iterator = std::reverse_iterator; protected: - T _arr[N] = {}; static constexpr const size_type _len = N; + T _arr[N] = {}; size_type _size = 0; public: @@ -51,7 +51,9 @@ namespace cc { template constexpr const_vector(InputIt first, InputIt last); - constexpr const_vector(const const_vector& other) noexcept; + constexpr const_vector(const const_vector& other) noexcept; + template + constexpr const_vector(const const_vector& other); constexpr const_vector(const_vector&& other) noexcept; constexpr ~const_vector() = default; // elements in static array should be destroyed automatically @@ -217,25 +219,33 @@ namespace cc { template template constexpr const_vector::const_vector(InputIt first, InputIt last) - : _size(std::distance(first, last)) { - //static_assert(std::distance(first, last) > N, "tried inserting more elements than const_vector is in size"); - _size = std::distance(first, last); + : _size(std::distance(first, last)) + { + if (std::distance(first, last) > N) throw std::invalid_argument("tried inserting more elements than const_vector is in size"); std::copy(first, last, _arr); - } + } + + template + constexpr const_vector::const_vector(const const_vector &other) noexcept + : _size(other._size) + { + std::copy(other.begin(), other.end(), _arr); + _size = other._size; + } template - constexpr const_vector::const_vector(const const_vector &other) noexcept - : _size(other._size) + template + constexpr const_vector::const_vector(const const_vector &other) + : _size(other.size()) { - if (N >= other._size) throw std::invalid_argument("size of other has to be equal to or smaller than this"); - std::copy(other._arr, other._arr, _arr); - } + if (_len <= other.size()) throw std::invalid_argument("size of other has to be equal to or smaller than this"); + std::copy(other.begin(), other.end(), _arr); + } template constexpr const_vector::const_vector(const_vector &&other) noexcept : _size(other._size) { - static_assert(N == other._len, "size of const_vectors does not match"); std::move(other.begin(), other.end(), _arr); } diff --git a/test/test_main.cpp b/test/test_main.cpp index 6a29c5f..ed24686 100644 --- a/test/test_main.cpp +++ b/test/test_main.cpp @@ -26,7 +26,8 @@ class test_const_vector; #define ASSERT_ALL_VEC_EQ(vec, eq) ASSERT_ALL_EQ(vec._arr, vec._arr + vec._len, eq) #define ASSERT_RANGE_VEC_EQ(vec, startI, endI, eq) ASSERT_ALL_EQ((vec._arr + startI), (vec._arr + endI), eq) -#define ASSERT_VEC_ARR_EQ(vec, eq) ASSERT_ARR_EQ(vec._arr, vec._arr + vec._len, eq) +#define ASSERT_VEC_ARR_EQ(vec, eq) ASSERT_ARR_EQ(vec._arr, vec._arr + vec._size, eq) +#define ASSERT_VEC_EQ(vec1, vec2) ASSERT_ARR_EQ(vec1._arr, vec1._arr + vec1._size, vec2._arr) #define ASSERT_RANGE_VEC_ARR_EQ(vec, startI, endI, eq) ASSERT_ARR_EQ((vec._arr + startI), (vec._arr + endI), eq) @@ -350,7 +351,7 @@ class test_const_vector { return true; } - + static consteval bool test_constructor_initializer_list() { #pragma message("Testing constructor 'const_vector(std::initializer_list list)'") @@ -439,8 +440,7 @@ class test_const_vector { return true; } - - + static consteval bool test_constructor_iterator() { #pragma message("Testing constructor 'const_vector(const_vector(InputIt first, InputIt last)'") @@ -449,7 +449,7 @@ class test_const_vector { constexpr cc::const_vector vi2(std::begin(C_VI_TEST_ARR2), std::end(C_VI_TEST_ARR2)); constexpr cc::const_vector vi3(STD_VI_TEST_ARR1.begin(), STD_VI_TEST_ARR1.end()); constexpr cc::const_vector vi4(STD_VI_TEST_ARR2.begin(), STD_VI_TEST_ARR2.end()); - + ASSERT(vi1._len == TEST_VEC1_CAPACITY) ASSERT(vi2._len == TEST_VEC2_CAPACITY) ASSERT(vi1._size == VI_TEST_ARR1_LEN) @@ -467,7 +467,7 @@ class test_const_vector { ASSERT_RANGE_VEC_ARR_EQ(vi4, 0, VI_TEST_ARR2_LEN, C_VI_TEST_ARR2) ASSERT_RANGE_VEC_EQ(vi4, VI_TEST_ARR2_LEN, TEST_VEC2_CAPACITY, int()) - + constexpr cc::const_vector vc1(std::begin(C_VC_TEST_ARR1), std::end(C_VC_TEST_ARR1)); constexpr cc::const_vector vc2(std::begin(C_VC_TEST_ARR2), std::end(C_VC_TEST_ARR2)); constexpr cc::const_vector vc3(STD_VC_TEST_ARR1.begin(), STD_VC_TEST_ARR1.end()); @@ -490,7 +490,7 @@ class test_const_vector { ASSERT_RANGE_VEC_ARR_EQ(vc4, 0, VC_TEST_ARR2_LEN, C_VC_TEST_ARR2) ASSERT_RANGE_VEC_EQ(vc4, VC_TEST_ARR2_LEN, TEST_VEC2_CAPACITY, char()) - + constexpr cc::const_vector vs1(std::begin(C_VS_TEST_ARR1), std::end(C_VS_TEST_ARR1)); constexpr cc::const_vector vs2(std::begin(C_VS_TEST_ARR2), std::end(C_VS_TEST_ARR2)); constexpr cc::const_vector vs3(STD_VS_TEST_ARR1.begin(), STD_VS_TEST_ARR1.end()); @@ -509,7 +509,7 @@ class test_const_vector { ASSERT_RANGE_VEC_ARR_EQ(vs3, 0, VS_TEST_ARR1_LEN, C_VS_TEST_ARR1) ASSERT_RANGE_VEC_ARR_EQ(vs4, 0, VS_TEST_ARR2_LEN, C_VS_TEST_ARR2) - + constexpr cc::const_vector vo1(std::begin(C_VO_TEST_ARR1), std::end(C_VO_TEST_ARR1)); constexpr cc::const_vector vo2(std::begin(C_VO_TEST_ARR2), std::end(C_VO_TEST_ARR2)); constexpr cc::const_vector vo3(STD_VO_TEST_ARR1.begin(), STD_VO_TEST_ARR1.end()); @@ -532,10 +532,169 @@ class test_const_vector { ASSERT_RANGE_VEC_ARR_EQ(vo4, 0, VO_TEST_ARR2_LEN, C_VO_TEST_ARR2) ASSERT_RANGE_VEC_EQ(vo4, VO_TEST_ARR2_LEN, TEST_VEC2_CAPACITY, TestStruct {}) + return true; + } + + static consteval bool test_constructor_copy() { + +#pragma message("Testing copy constructors") + + constexpr cc::const_vector vi1(C_VI_TEST_ARR1); + constexpr cc::const_vector vi2(C_VI_TEST_ARR2); + constexpr cc::const_vector vi1c(vi1); + constexpr cc::const_vector vi2c(vi2); + constexpr cc::const_vector vi3(vi1); + constexpr cc::const_vector vi4(vi2); + + ASSERT(vi1c._len == vi1._len) + ASSERT(vi2c._len == vi2._len) + ASSERT(vi1c._size == vi1._size) + ASSERT(vi2c._size == vi2._size) + ASSERT_VEC_EQ(vi1c, vi1) + ASSERT_VEC_EQ(vi2c, vi2) + ASSERT(vi3._len == TEST_VEC1_CAPACITY) + ASSERT(vi4._len == TEST_VEC2_CAPACITY) + ASSERT(vi3._size == vi1._size) + ASSERT(vi4._size == vi2._size) + ASSERT_VEC_EQ(vi3, vi1) + ASSERT_VEC_EQ(vi4, vi2) + + + constexpr cc::const_vector vc1(C_VC_TEST_ARR1); + constexpr cc::const_vector vc2(C_VC_TEST_ARR2); + constexpr cc::const_vector vc1c(vc1); + constexpr cc::const_vector vc2c(vc2); + constexpr cc::const_vector vc3(vc1); + constexpr cc::const_vector vc4(vc2); + + ASSERT(vc1c._len == vc1._len) + ASSERT(vc2c._len == vc2._len) + ASSERT(vc1c._size == vc1._size) + ASSERT(vc2c._size == vc2._size) + ASSERT_VEC_EQ(vc1c, vc1) + ASSERT_VEC_EQ(vc2c, vc2) + ASSERT(vc3._len == TEST_VEC1_CAPACITY) + ASSERT(vc4._len == TEST_VEC2_CAPACITY) + ASSERT(vc3._size == vc1._size) + ASSERT(vc4._size == vc2._size) + ASSERT_VEC_EQ(vc3, vc1) + ASSERT_VEC_EQ(vc4, vc2) + + + constexpr cc::const_vector vs1(C_VS_TEST_ARR1); + constexpr cc::const_vector vs2(C_VS_TEST_ARR2); + constexpr cc::const_vector vs1c(vs1); + constexpr cc::const_vector vs2c(vs2); + constexpr cc::const_vector vs3(vs1); + constexpr cc::const_vector vs4(vs2); + + ASSERT(vs1c._len == vs1._len) + ASSERT(vs2c._len == vs2._len) + ASSERT(vs1c._size == vs1._size) + ASSERT(vs2c._size == vs2._size) + ASSERT_VEC_EQ(vs1c, vs1) + ASSERT_VEC_EQ(vs2c, vs2) + ASSERT(vs3._len == TEST_VEC1_CAPACITY) + ASSERT(vs4._len == TEST_VEC2_CAPACITY) + ASSERT(vs3._size == vs1._size) + ASSERT(vs4._size == vs2._size) + ASSERT_VEC_EQ(vs3, vs1) + ASSERT_VEC_EQ(vs4, vs2) + + + constexpr cc::const_vector vo1(C_VO_TEST_ARR1); + constexpr cc::const_vector vo2(C_VO_TEST_ARR2); + constexpr cc::const_vector vo1c(vo1); + constexpr cc::const_vector vo2c(vo2); + constexpr cc::const_vector vo3(vo1); + constexpr cc::const_vector vo4(vo2); + + ASSERT(vo1c._len == vo1._len) + ASSERT(vo2c._len == vo2._len) + ASSERT(vo1c._size == vo1._size) + ASSERT(vo2c._size == vo2._size) + ASSERT_VEC_EQ(vo1c, vo1) + ASSERT_VEC_EQ(vo2c, vo2) + ASSERT(vo3._len == TEST_VEC1_CAPACITY) + ASSERT(vo4._len == TEST_VEC2_CAPACITY) + ASSERT(vo3._size == vo1._size) + ASSERT(vo4._size == vo2._size) + ASSERT_VEC_EQ(vo3, vo1) + ASSERT_VEC_EQ(vo4, vo2) + return true; } + static consteval bool test_constructor_move() { + +#pragma message("Testing move constructor") + + constexpr cc::const_vector vi1(C_VI_TEST_ARR1); + constexpr cc::const_vector vi2(C_VI_TEST_ARR2); + constexpr cc::const_vector vi1c(vi1); + constexpr cc::const_vector vi2c(vi2); + constexpr cc::const_vector vi3(const_cast&&>(vi1)); + constexpr cc::const_vector vi4(const_cast&&>(vi2)); + + ASSERT(vi3._len == vi1c._len) + ASSERT(vi4._len == vi2c._len) + ASSERT(vi3._size == vi1c._size) + ASSERT(vi4._size == vi2c._size) + ASSERT_VEC_EQ(vi3, vi1c) + ASSERT_VEC_EQ(vi4, vi2c) + + + constexpr cc::const_vector vc1(C_VC_TEST_ARR1); + constexpr cc::const_vector vc2(C_VC_TEST_ARR2); + constexpr cc::const_vector vc1c(vc1); + constexpr cc::const_vector vc2c(vc2); + constexpr cc::const_vector vc3(const_cast&&>(vc1)); + constexpr cc::const_vector vc4(const_cast&&>(vc2)); + + ASSERT(vi3._len == vi1c._len) + ASSERT(vi4._len == vi2c._len) + ASSERT(vi3._size == vi1c._size) + ASSERT(vi4._size == vi2c._size) + ASSERT_VEC_EQ(vi3, vi1c) + ASSERT_VEC_EQ(vi4, vi2c) + + + constexpr cc::const_vector vs1(C_VS_TEST_ARR1); + constexpr cc::const_vector vs2(C_VS_TEST_ARR2); + constexpr cc::const_vector vs1c(vs1); + constexpr cc::const_vector vs2c(vs2); + constexpr cc::const_vector vs3(const_cast&&>(vs1)); + constexpr cc::const_vector vs4(const_cast&&>(vs2)); + + ASSERT(vs3._len == vs1c._len) + ASSERT(vs4._len == vs2c._len) + ASSERT(vs3._size == vs1c._size) + ASSERT(vs4._size == vs2c._size) + ASSERT_VEC_EQ(vs3, vs1c) + ASSERT_VEC_EQ(vs4, vs2c) + + + constexpr cc::const_vector vo1(C_VO_TEST_ARR1); + constexpr cc::const_vector vo2(C_VO_TEST_ARR2); + constexpr cc::const_vector vo1c(vo1); + constexpr cc::const_vector vo2c(vo2); + constexpr cc::const_vector vo3(const_cast&&>(vo1)); + constexpr cc::const_vector vo4(const_cast&&>(vo2)); + + ASSERT(vo3._len == vo1c._len) + ASSERT(vo4._len == vo2c._len) + ASSERT(vo3._size == vo1c._size) + ASSERT(vo4._size == vo2c._size) + ASSERT_VEC_EQ(vo3, vo1c) + ASSERT_VEC_EQ(vo4, vo2c) + + + return true; + } + + + }; int main(int, char *[]) @@ -548,7 +707,8 @@ int main(int, char *[]) std::cout << "Test of constructor 'const_vector(const value_type (&array)[N])': " << test_const_vector::test_constructor_array() << std::endl; std::cout << "Test of constructor 'const_vector(std::initializer_list values)': " << test_const_vector::test_constructor_initializer_list() << std::endl; std::cout << "Test of constructor 'const_vector(InputIt first, InputIt last)': " << test_const_vector::test_constructor_iterator() << std::endl; - + std::cout << "Test of copy constructors: " << test_const_vector::test_constructor_copy() << std::endl; + std::cout << "Test of move constructor: " << test_const_vector::test_constructor_move() << std::endl; return 0; }