diff --git a/include/etl/const_map.h b/include/etl/const_map.h index af9905f7..23e0f46c 100644 --- a/include/etl/const_map.h +++ b/include/etl/const_map.h @@ -55,18 +55,14 @@ namespace etl { public: - using key_type = TKey; - using value_type = ETL_OR_STD::pair; - using mapped_type = TMapped ; - using key_compare = TKeyCompare; - using const_reference = const value_type&; - using const_pointer = const value_type*; - using const_iterator = const value_type*; - using size_type = size_t; - - /// Defines the parameter types - using const_key_reference = const key_type&; - using const_mapped_reference = const mapped_type&; + using key_type = TKey; + using value_type = ETL_OR_STD::pair; + using mapped_type = TMapped ; + using key_compare = TKeyCompare; + using const_reference = const value_type&; + using const_pointer = const value_type*; + using const_iterator = const value_type*; + using size_type = size_t; //********************************************************************* /// How to compare elements and keys. @@ -82,7 +78,7 @@ namespace etl } // Compare value type and key. - ETL_CONSTEXPR14 bool operator ()(const value_type& element, const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 bool operator ()(const value_type& element, const key_type& key) const ETL_NOEXCEPT { return kcompare(element.first, key); } @@ -96,7 +92,7 @@ namespace etl } // Compare key and value type. - ETL_CONSTEXPR14 bool operator ()(const_key_reference key, const value_type& element) const ETL_NOEXCEPT + ETL_CONSTEXPR14 bool operator ()(const key_type& key, const value_type& element) const ETL_NOEXCEPT { return kcompare(key, element.first); } @@ -165,10 +161,10 @@ namespace etl //************************************************************************* ///\brief Index operator. ///\param key The key of the element to return. - ///\return A const_mapped_reference to the mapped value at the index. + ///\return A const mapped_type& to the mapped value at the index. /// Undefined behaviour if the key is not in the map. //************************************************************************* - ETL_CONSTEXPR14 const_mapped_reference operator[](const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 const mapped_type& operator[](const key_type& key) const ETL_NOEXCEPT { const_iterator itr = find(key); @@ -179,11 +175,11 @@ namespace etl ///\brief Key index operator. /// Enabled for transparent comparators. ///\param key The key of the element to return. - ///\return A const_mapped_reference to the mapped value at the key index. + ///\return A const mapped_type& to the mapped value at the key index. /// Undefined behaviour if the key is not in the map. //************************************************************************* template ::value, int> = 0> - ETL_CONSTEXPR14 const_mapped_reference operator[](const K& key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 const mapped_type& operator[](const K& key) const ETL_NOEXCEPT { const_iterator itr = find(key); @@ -193,10 +189,10 @@ namespace etl //************************************************************************* ///\brief Gets the mapped value at the key index. ///\param key The key of the element to return. - ///\return A const_mapped_reference to the mapped value at the index. + ///\return A const mapped_type& to the mapped value at the index. /// Undefined behaviour if the key is not in the map. //************************************************************************* - ETL_CONSTEXPR14 const_mapped_reference at(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 const mapped_type& at(const key_type& key) const ETL_NOEXCEPT { const_iterator itr = find(key); @@ -207,11 +203,11 @@ namespace etl ///\brief Gets the mapped value at the key index. /// Enabled if the comparator is transparent. ///\param key The key of the element to return. - ///\return A const_mapped_reference to the mapped value at the index. + ///\return A const mapped_type& to the mapped value at the index. /// Undefined behaviour if the key is not in the map. //************************************************************************* template ::value, int> = 0> - ETL_CONSTEXPR14 const_mapped_reference at(const K& key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 const mapped_type& at(const K& key) const ETL_NOEXCEPT { const_iterator itr = find(key); @@ -224,7 +220,7 @@ namespace etl ///\return A const_iterator to the mapped value at the index, /// or end() if not found. //************************************************************************* - ETL_CONSTEXPR14 const_iterator find(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 const_iterator find(const key_type& key) const ETL_NOEXCEPT { const_iterator itr = lower_bound(key); @@ -234,7 +230,6 @@ namespace etl } return end(); - } //************************************************************************* @@ -262,7 +257,7 @@ namespace etl ///\param key The key of the element to check. ///\return true if the map contains an element with key. //************************************************************************* - ETL_CONSTEXPR14 bool contains(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 bool contains(const key_type& key) const ETL_NOEXCEPT { return find(key) != end(); } @@ -284,7 +279,7 @@ namespace etl ///\param key The key of the element to count. ///\return 0 or 1 //************************************************************************* - ETL_CONSTEXPR14 size_type count(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 size_type count(const key_type& key) const ETL_NOEXCEPT { return contains(key) ? 1 : 0; } @@ -309,7 +304,7 @@ namespace etl ///\param key The key of the element ///\return etl::pair or std::pair containing a pair of iterators. //************************************************************************* - ETL_CONSTEXPR14 ETL_OR_STD::pair equal_range(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 ETL_OR_STD::pair equal_range(const key_type& key) const ETL_NOEXCEPT { return etl::equal_range(begin(), end(), key, vcompare); } @@ -335,7 +330,7 @@ namespace etl ///\param key The key of the element ///\return const_iterator to the element or end() //************************************************************************* - ETL_CONSTEXPR14 const_iterator lower_bound(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 const_iterator lower_bound(const key_type& key) const ETL_NOEXCEPT { return etl::lower_bound(begin(), end(), key, vcompare); } @@ -359,7 +354,7 @@ namespace etl ///\param key The key of the element ///\return const_iterator to the element or end() //************************************************************************* - ETL_CONSTEXPR14 const_iterator upper_bound(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 const_iterator upper_bound(const key_type& key) const ETL_NOEXCEPT { return etl::upper_bound(begin(), end(), key, vcompare); } @@ -459,7 +454,7 @@ namespace etl //********************************************************************* /// Check to see if the keys are equal. //********************************************************************* - ETL_CONSTEXPR14 bool keys_are_equal(const_key_reference key1, const_key_reference key2) const ETL_NOEXCEPT + ETL_CONSTEXPR14 bool keys_are_equal(const key_type& key1, const key_type& key2) const ETL_NOEXCEPT { return !key_compare()(key1, key2) && !key_compare()(key2, key1); } @@ -500,10 +495,6 @@ namespace etl using const_iterator = typename base_t::const_iterator; using size_type = typename base_t::size_type; - /// Defines the parameter types - using const_key_reference = const key_type&; - using const_mapped_reference = const mapped_type&; - static_assert((etl::is_default_constructible::value), "key_type must be default constructible"); static_assert((etl::is_default_constructible::value), "mapped_type must be default constructible"); @@ -555,10 +546,6 @@ namespace etl using const_iterator = typename base_t::const_iterator; using size_type = typename base_t::size_type; - /// Defines the parameter types - using const_key_reference = const key_type&; - using const_mapped_reference = const mapped_type&; - static_assert((etl::is_default_constructible::value), "key_type must be default constructible"); static_assert((etl::is_default_constructible::value), "mapped_type must be default constructible"); @@ -607,7 +594,7 @@ namespace etl ETL_CONSTEXPR14 bool operator ==(const etl::iconst_map& lhs, const etl::iconst_map& rhs) ETL_NOEXCEPT { - return etl::equal(lhs.begin(), lhs.end(), rhs.begin()); + return (lhs.size() == rhs.size()) && etl::equal(lhs.begin(), lhs.end(), rhs.begin()); } //************************************************************************* diff --git a/include/etl/const_multimap.h b/include/etl/const_multimap.h index 7b7c3968..afcd90b9 100644 --- a/include/etl/const_multimap.h +++ b/include/etl/const_multimap.h @@ -64,10 +64,6 @@ namespace etl using const_iterator = const value_type*; using size_type = size_t; - /// Defines the parameter types - using const_key_reference = const key_type&; - using const_mapped_reference = const mapped_type&; - //********************************************************************* /// How to compare elements and keys. //********************************************************************* @@ -82,7 +78,7 @@ namespace etl } // Compare value type and key. - ETL_CONSTEXPR14 bool operator ()(const value_type& element, const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 bool operator ()(const value_type& element, const key_type& key) const ETL_NOEXCEPT { return kcompare(element.first, key); } @@ -96,7 +92,7 @@ namespace etl } // Compare key and value type. - ETL_CONSTEXPR14 bool operator ()(const_key_reference key, const value_type& element) const ETL_NOEXCEPT + ETL_CONSTEXPR14 bool operator ()(const key_type& key, const value_type& element) const ETL_NOEXCEPT { return kcompare(key, element.first); } @@ -173,7 +169,7 @@ namespace etl ///\return A const_iterator to the mapped value at the index, /// or end() if not found. //************************************************************************* - ETL_CONSTEXPR14 const_iterator find(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 const_iterator find(const key_type& key) const ETL_NOEXCEPT { const_iterator itr = lower_bound(key); @@ -210,7 +206,7 @@ namespace etl ///\param key The key of the element to check. ///\return true if the map contains an element with key. //************************************************************************* - ETL_CONSTEXPR14 bool contains(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 bool contains(const key_type& key) const ETL_NOEXCEPT { return find(key) != end(); } @@ -232,7 +228,7 @@ namespace etl ///\param key The key of the element to count. ///\return 0 or 1 //************************************************************************* - ETL_CONSTEXPR14 size_type count(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 size_type count(const key_type& key) const ETL_NOEXCEPT { auto range = equal_range(key); @@ -261,7 +257,7 @@ namespace etl ///\param key The key of the element ///\return etl::pair or std::pair containing a pair of iterators. //************************************************************************* - ETL_CONSTEXPR14 ETL_OR_STD::pair equal_range(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 ETL_OR_STD::pair equal_range(const key_type& key) const ETL_NOEXCEPT { return etl::equal_range(begin(), end(), key, vcompare); } @@ -287,7 +283,7 @@ namespace etl ///\param key The key of the element ///\return const_iterator to the element or end() //************************************************************************* - ETL_CONSTEXPR14 const_iterator lower_bound(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 const_iterator lower_bound(const key_type& key) const ETL_NOEXCEPT { return etl::lower_bound(begin(), end(), key, vcompare); } @@ -311,7 +307,7 @@ namespace etl ///\param key The key of the element ///\return const_iterator to the element or end() //************************************************************************* - ETL_CONSTEXPR14 const_iterator upper_bound(const_key_reference key) const ETL_NOEXCEPT + ETL_CONSTEXPR14 const_iterator upper_bound(const key_type& key) const ETL_NOEXCEPT { return etl::upper_bound(begin(), end(), key, vcompare); } @@ -411,7 +407,7 @@ namespace etl //********************************************************************* /// Check to see if the keys are equal. //********************************************************************* - ETL_CONSTEXPR14 bool keys_are_equal(const_key_reference key1, const_key_reference key2) const ETL_NOEXCEPT + ETL_CONSTEXPR14 bool keys_are_equal(const key_type& key1, const key_type& key2) const ETL_NOEXCEPT { return !key_compare()(key1, key2) && !key_compare()(key2, key1); } @@ -452,10 +448,6 @@ namespace etl using const_iterator = typename base_t::const_iterator; using size_type = typename base_t::size_type; - /// Defines the parameter types - using const_key_reference = const key_type&; - using const_mapped_reference = const mapped_type&; - static_assert((etl::is_default_constructible::value), "key_type must be default constructible"); static_assert((etl::is_default_constructible::value), "mapped_type must be default constructible"); @@ -508,10 +500,6 @@ namespace etl using const_iterator = typename base_t::const_iterator; using size_type = typename base_t::size_type; - /// Defines the parameter types - using const_key_reference = const key_type&; - using const_mapped_reference = const mapped_type&; - static_assert((etl::is_default_constructible::value), "key_type must be default constructible"); static_assert((etl::is_default_constructible::value), "mapped_type must be default constructible"); diff --git a/include/etl/const_multiset.h b/include/etl/const_multiset.h new file mode 100644 index 00000000..ee618480 --- /dev/null +++ b/include/etl/const_multiset.h @@ -0,0 +1,574 @@ +///\file + +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2025 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#ifndef ETL_CONST_MULTISET_INCLUDED +#define ETL_CONST_MULTISET_INCLUDED + +#include "platform.h" + +#if ETL_NOT_USING_CPP11 + #error NOT SUPPORTED FOR C++03 OR BELOW +#endif + +#include "algorithm.h" +#include "type_traits.h" +#include "functional.h" +#include "nth_type.h" +#include "span.h" + +#include "private/comparator_is_transparent.h" + +///\defgroup const_multiset const_multiset +///\ingroup containers + +namespace etl +{ + template > + class iconst_multiset + { + public: + + using key_type = TKey; + using value_type = TKey; + using key_compare = TKeyCompare; + using value_compare = TKeyCompare; + using const_reference = const value_type&; + using const_pointer = const value_type*; + using const_iterator = const value_type*; + using size_type = size_t; + + //************************************************************************* + /// Check that the elements are valid for a multiset. + /// The elements must be sorted. + /// \return true if the elements are valid for the multiset. + //************************************************************************* + ETL_CONSTEXPR14 bool is_valid() const ETL_NOEXCEPT + { + return etl::is_sorted(begin(), end(), vcompare); + } + + //************************************************************************* + ///\brief Gets the beginning of the multiset. + ///\return const_iterator to the beginning of the multiset. + //************************************************************************* + ETL_CONSTEXPR14 const_iterator begin() const ETL_NOEXCEPT + { + return element_list; + } + + //************************************************************************* + ///\brief Gets the beginning of the multiset. + ///\return const_iterator to the beginning of the multiset. + //************************************************************************* + ETL_CONSTEXPR14 const_iterator cbegin() const ETL_NOEXCEPT + { + return element_list; + } + + //************************************************************************* + ///\brief Gets the end of the multiset. + ///\return const_iterator to the end of the multiset. + //************************************************************************* + ETL_CONSTEXPR14 const_iterator end() const ETL_NOEXCEPT + { + return element_list_end; + } + + //************************************************************************* + ///\brief Gets the end of the multiset. + ///\return const_iterator to the end of the multiset. + //************************************************************************* + ETL_CONSTEXPR14 const_iterator cend() const ETL_NOEXCEPT + { + return element_list_end; + } + + //************************************************************************* + ///\brief Gets the beginning of the multiset. + ///\return const_pointer to the beginning of the multiset. + //************************************************************************* + ETL_CONSTEXPR14 const_pointer data() const ETL_NOEXCEPT + { + return element_list; + } + + //************************************************************************* + ///\brief Gets a const_iterator to the value at the key index. + ///\param key The key of the element to find. + ///\return A const_iterator to the value at the index, + /// or end() if not found. + //************************************************************************* + ETL_CONSTEXPR14 const_iterator find(const key_type& key) const ETL_NOEXCEPT + { + const_iterator itr = lower_bound(key); + + if ((itr != end()) && (keys_are_equal(*itr, key))) + { + return itr; + } + + return end(); + } + + //************************************************************************* + ///\brief Gets a const_iterator to the value at the key index. + /// Enabled if the comparator is transparent. + ///\param key The key of the element to find. + ///\return A const_iterator to the value at the index, + /// or end() if not found. + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 const_iterator find(const K& key) const ETL_NOEXCEPT + { + const_iterator itr = lower_bound(key); + + if ((itr != end()) && (keys_are_equal(*itr, key))) + { + return itr; + } + + return end(); + } + + //************************************************************************* + ///\brief Checks if the multiset contains an element with key. + ///\param key The key of the element to check. + ///\return true if the multiset contains an element with key. + //************************************************************************* + ETL_CONSTEXPR14 bool contains(const key_type& key) const ETL_NOEXCEPT + { + return find(key) != end(); + } + + //************************************************************************* + ///\brief Checks if the multiset contains an element with key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element to check. + ///\return true if the multiset contains an element with key. + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 bool contains(const K& key) const ETL_NOEXCEPT + { + return find(key) != end(); + } + + //************************************************************************* + ///\brief Counts the numbeer elements with key. + ///\param key The key of the element to count. + ///\return 0 or 1 + //************************************************************************* + ETL_CONSTEXPR14 size_type count(const key_type& key) const ETL_NOEXCEPT + { + auto range = equal_range(key); + + return size_type(etl::distance(range.first, range.second)); + } + + //************************************************************************* + ///\brief Counts the numbeer elements with key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element to count. + ///\return 0 or 1 + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 size_type count(const K& key) const ETL_NOEXCEPT + { + auto range = equal_range(key); + + return size_type(etl::distance(range.first, range.second)); + } + + //************************************************************************* + ///\brief Returns a range containing all elements with the key. + /// The range is defined by a pair of two iterators, one to the + /// first element that is not less than the key and second to the first + /// element greater than the key. + ///\param key The key of the element + ///\return etl::pair or std::pair containing a pair of iterators. + //************************************************************************* + ETL_CONSTEXPR14 ETL_OR_STD::pair equal_range(const key_type& key) const ETL_NOEXCEPT + { + return etl::equal_range(begin(), end(), key, vcompare); + } + + //************************************************************************* + ///\brief Returns a range containing all elements with the key. + /// The range is defined by a pair of two iterators, one to the + /// first element that is not less than the key and second to the first + /// element greater than the key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element + ///\return etl::pair or std::pair containing a pair of iterators. + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 ETL_OR_STD::pair equal_range(const K& key) const ETL_NOEXCEPT + { + return etl::equal_range(begin(), end(), key, vcompare); + } + + //************************************************************************* + ///\brief Returns a const_iterator to the first element that is not less than the key. + /// Returns a const_iterator to the first element that is not less than the key. + ///\param key The key of the element + ///\return const_iterator to the element or end() + //************************************************************************* + ETL_CONSTEXPR14 const_iterator lower_bound(const key_type& key) const ETL_NOEXCEPT + { + return etl::lower_bound(begin(), end(), key, vcompare); + } + + //************************************************************************* + ///\brief Returns a const_iterator to the first element that is not less than the key. + /// Returns a const_iterator to the first element that is not less than the key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element + ///\return const_iterator to the element or end() + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 const_iterator lower_bound(const K& key) const ETL_NOEXCEPT + { + return etl::lower_bound(begin(), end(), key, vcompare); + } + + //************************************************************************* + ///\brief Returns a const_iterator to the first element that is greater than the key. + /// Returns a const_iterator to the first element that is greater than the key. + ///\param key The key of the element + ///\return const_iterator to the element or end() + //************************************************************************* + ETL_CONSTEXPR14 const_iterator upper_bound(const key_type& key) const ETL_NOEXCEPT + { + return etl::upper_bound(begin(), end(), key, vcompare); + } + + //************************************************************************* + ///\brief Returns a const_iterator to the first element that is greater than the key. + /// Returns a const_iterator to the first element that is greater than the key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element + ///\return const_iterator to the element or end() + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 const_iterator upper_bound(const K& key) const ETL_NOEXCEPT + { + return etl::upper_bound(begin(), end(), key, vcompare); + } + + //************************************************************************* + /// Checks if the multiset is empty. + ///\return true if the multiset is empty. + //************************************************************************* + ETL_CONSTEXPR14 size_type empty() const ETL_NOEXCEPT + { + return size() == 0U; + } + + //************************************************************************* + /// Checks if the multiset is full. + ///\return true if the multiset is full. + //************************************************************************* + ETL_CONSTEXPR14 size_type full() const ETL_NOEXCEPT + { + return (max_elements != 0) && (size() == max_elements); + } + + //************************************************************************* + /// Gets the size of the multiset. + ///\return The size of the multiset. + //************************************************************************* + ETL_CONSTEXPR14 size_type size() const ETL_NOEXCEPT + { + return size_type(element_list_end - element_list); + } + + //************************************************************************* + /// Gets the maximum size of the multiset. + ///\return The maximum size of the multiset. + //************************************************************************* + ETL_CONSTEXPR14 size_type max_size() const ETL_NOEXCEPT + { + return max_elements; + } + + //************************************************************************* + /// Gets the capacity of the multiset. + /// This is always equal to max_size(). + ///\return The capacity of the multiset. + //************************************************************************* + ETL_CONSTEXPR14 size_type capacity() const ETL_NOEXCEPT + { + return max_elements; + } + + //************************************************************************* + /// How to compare two key elements. + ///\return An instance of the key_compare type. + //************************************************************************* + ETL_CONSTEXPR14 key_compare key_comp() const ETL_NOEXCEPT + { + return kcompare; + } + + //************************************************************************* + /// How to compare two value elements. + ///\return An instance of the value_compare type. + //************************************************************************* + ETL_CONSTEXPR14 value_compare value_comp() const ETL_NOEXCEPT + { + return vcompare; + } + + protected: + + //************************************************************************* + /// Constructor + //************************************************************************* + template + ETL_CONSTEXPR14 explicit iconst_multiset(const value_type* element_list_, size_type size_, size_type max_elements_) ETL_NOEXCEPT + : element_list(element_list_) + , element_list_end{element_list_ + size_} + , max_elements(max_elements_) + { + } + + private: + + //********************************************************************* + /// Check to see if the keys are equal. + //********************************************************************* + ETL_CONSTEXPR14 bool keys_are_equal(const key_type& key1, const key_type& key2) const ETL_NOEXCEPT + { + return !key_compare()(key1, key2) && !key_compare()(key2, key1); + } + + //********************************************************************* + /// Check to see if the keys are equal. + /// Enabled if the comparator is transparent. + //********************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 bool keys_are_equal(const K1& key1, const K2& key2) const ETL_NOEXCEPT + { + return !key_compare()(key1, key2) && !key_compare()(key2, key1); + } + + key_compare kcompare; + value_compare vcompare; + + const value_type* element_list; + const value_type* element_list_end; + size_type max_elements; + }; + + //************************************************************************* + /// Multiset type designed for constexpr. + //************************************************************************* + template > + class const_multiset : public iconst_multiset + { + public: + + using base_t = iconst_multiset; + + using key_type = typename base_t::key_type; + using value_type = typename base_t::value_type; + using key_compare = typename base_t::key_compare; + using const_reference = typename base_t::const_reference; + using const_pointer = typename base_t::const_pointer; + using const_iterator = typename base_t::const_iterator; + using size_type = typename base_t::size_type; + + static_assert((etl::is_default_constructible::value), "key_type must be default constructible"); + + //************************************************************************* + ///\brief Construct a const_set from a variadic list of elements. + /// Static asserts if the element type is not constructible. + /// Static asserts if the elements are not of type value_type. + /// Static asserts if the number of elements is greater than the capacity of the const_set. + //************************************************************************* + template + ETL_CONSTEXPR14 explicit const_multiset(TElements&&... elements) ETL_NOEXCEPT + : iconst_multiset(element_list, sizeof...(elements), Size) + , element_list{etl::forward(elements)...} + { + static_assert((etl::are_all_same...>::value), "All elements must be value_type"); + static_assert(sizeof...(elements) <= Size, "Number of elements exceeds capacity"); + } + + private: + + value_type element_list[Size]; + }; + + //************************************************************************* + /// Template deduction guides. + //************************************************************************* +#if ETL_USING_CPP17 + template + const_multiset(TElements...) -> const_multiset, sizeof...(TElements)>; +#endif + + //********************************************************************* + /// Multiset type designed for constexpr. + //********************************************************************* + template > + class const_multiset_ext : public iconst_multiset + { + public: + + using base_t = iconst_multiset; + + using key_type = typename base_t::key_type; + using value_type = typename base_t::value_type; + using key_compare = typename base_t::key_compare; + using const_reference = typename base_t::const_reference; + using const_pointer = typename base_t::const_pointer; + using const_iterator = typename base_t::const_iterator; + using size_type = typename base_t::size_type; + + static_assert((etl::is_default_constructible::value), "key_type must be default constructible"); + + //************************************************************************* + ///\brief Default construct a const_multiset. + //************************************************************************* + ETL_CONSTEXPR14 const_multiset_ext() ETL_NOEXCEPT + : iconst_multiset(nullptr, 0, 0) + { + } + + //************************************************************************* + ///\brief Construct a const_multiset from a variadic list of elements. + //************************************************************************* + template + ETL_CONSTEXPR14 explicit const_multiset_ext(const etl::span& sp) ETL_NOEXCEPT + : iconst_multiset(sp.data(), Size, Size) + { + } + + //************************************************************************* + ///\brief Construct a const_multiset from an array. + //************************************************************************* + template + ETL_CONSTEXPR14 explicit const_multiset_ext(const value_type(&begin_)[Size]) ETL_NOEXCEPT + : iconst_multiset(begin_, Size, Size) + { + } + }; + + //************************************************************************* + /// Template deduction guides. + //************************************************************************* +#if ETL_USING_CPP17 + template + const_multiset_ext(const etl::span&) -> const_multiset_ext; + + template + const_multiset_ext(const TElements(&)[N]) -> const_multiset_ext; +#endif + + //************************************************************************* + /// Equality test. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator ==(const etl::iconst_multiset& lhs, + const etl::iconst_multiset& rhs) ETL_NOEXCEPT + { + return (lhs.size() == rhs.size()) && etl::equal(lhs.begin(), lhs.end(), rhs.begin()); + } + + //************************************************************************* + /// Inequality test. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator !=(const etl::iconst_multiset& lhs, + const etl::iconst_multiset& rhs) ETL_NOEXCEPT + { + return !(lhs == rhs); + } + + //************************************************************************* + /// Less than operator. + ///\param lhs Reference to the first list. + ///\param rhs Reference to the second list. + ///\return true if the first list is lexicographically less than the + /// second, otherwise false. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator <(const etl::iconst_multiset& lhs, + const etl::iconst_multiset& rhs) ETL_NOEXCEPT + { + return etl::lexicographical_compare(lhs.begin(), lhs.end(), + rhs.begin(), rhs.end(), + lhs.value_comp()); + } + + //************************************************************************* + /// Greater than operator. + ///\param lhs Reference to the first list. + ///\param rhs Reference to the second list. + ///\return true if the first list is lexicographically greater than the + /// second, otherwise false. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator >(const etl::iconst_multiset& lhs, + const etl::iconst_multiset& rhs) ETL_NOEXCEPT + { + return (rhs < lhs); + } + + //************************************************************************* + /// Less than or equal operator. + ///\param lhs Reference to the first list. + ///\param rhs Reference to the second list. + ///\return true if the first list is lexicographically less than or equal + /// to the second, otherwise false. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator <=(const etl::iconst_multiset& lhs, + const etl::iconst_multiset& rhs) ETL_NOEXCEPT + { + return !(rhs < lhs); + } + + //************************************************************************* + /// Greater than or equal operator. + ///\param lhs Reference to the first list. + ///\param rhs Reference to the second list. + ///\return true if the first list is lexicographically greater than or + /// equal to the second, otherwise false. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator >=(const etl::iconst_multiset& lhs, + const etl::iconst_multiset& rhs) ETL_NOEXCEPT + { + return !(lhs < rhs); + } +} + +#endif diff --git a/include/etl/const_set.h b/include/etl/const_set.h new file mode 100644 index 00000000..4ef5194a --- /dev/null +++ b/include/etl/const_set.h @@ -0,0 +1,554 @@ +///\file + +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2025 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#ifndef ETL_CONST_SET_INCLUDED +#define ETL_CONST_SET_INCLUDED + +#include "platform.h" + +#if ETL_NOT_USING_CPP11 + #error NOT SUPPORTED FOR C++03 OR BELOW +#endif + +#include "algorithm.h" +#include "type_traits.h" +#include "functional.h" +#include "nth_type.h" +#include "span.h" + +#include "private/comparator_is_transparent.h" + +///\defgroup const_set const_set +///\ingroup containers + +namespace etl +{ + template + class iconst_set + { + public: + + using key_type = TKey; + using value_type = TKey; + using key_compare = TKeyCompare; + using value_compare = TKeyCompare; + using const_reference = const value_type&; + using const_pointer = const value_type*; + using const_iterator = const value_type*; + using size_type = size_t; + + //************************************************************************* + /// Check that the elements are valid for a set. + /// The elements must be sorted and contain no duplicates. + /// \return true if the elements are valid for the set. + //************************************************************************* + ETL_CONSTEXPR14 bool is_valid() const ETL_NOEXCEPT + { + return etl::is_unique_sorted(begin(), end(), vcompare); + } + + //************************************************************************* + ///\brief Returns a const_iterator to the beginning of the set. + //************************************************************************* + ETL_CONSTEXPR14 const_iterator begin() const ETL_NOEXCEPT + { + return element_list; + } + + //************************************************************************* + ///\brief Returns a const_iterator to the beginning of the set. + //************************************************************************* + ETL_CONSTEXPR14 const_iterator cbegin() const ETL_NOEXCEPT + { + return element_list; + } + + //************************************************************************* + ///\brief Returns a const_iterator to the end of the set. + //************************************************************************* + ETL_CONSTEXPR14 const_iterator end() const ETL_NOEXCEPT + { + return element_list_end; + } + + //************************************************************************* + ///\brief Returns a const_iterator to the end of the set. + //************************************************************************* + ETL_CONSTEXPR14 const_iterator cend() const ETL_NOEXCEPT + { + return element_list_end; + } + + //************************************************************************* + ///\brief Returns a const_pointer to the beginning of the set. + //************************************************************************* + ETL_CONSTEXPR14 const_pointer data() const ETL_NOEXCEPT + { + return element_list; + } + + //************************************************************************* + ///\brief Gets a const_iterator to the key. + ///\param key The key of the element to find. + ///\return A const_iterator to the key, + /// or end() if not found. + //************************************************************************* + ETL_CONSTEXPR14 const_iterator find(const key_type& key) const ETL_NOEXCEPT + { + const_iterator itr = lower_bound(key); + + if ((itr != end()) && (keys_are_equal(*itr, key))) + { + return itr; + } + + return end(); + } + + //************************************************************************* + ///\brief Gets a const_iterator to the key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element to find. + ///\return A const_iterator to the key, + /// or end() if not found. + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 const_iterator find(const K& key) const ETL_NOEXCEPT + { + const_iterator itr = lower_bound(key); + + if ((itr != end()) && (keys_are_equal(*itr, key))) + { + return itr; + } + + return end(); + } + + //************************************************************************* + ///\brief Checks if the set contains an element with key. + ///\param key The key of the element to check. + ///\return true if the set contains an element with key. + //************************************************************************* + ETL_CONSTEXPR14 bool contains(const key_type& key) const ETL_NOEXCEPT + { + return find(key) != end(); + } + + //************************************************************************* + ///\brief Checks if the set contains an element with key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element to check. + ///\return true if the set contains an element with key. + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 bool contains(const K& key) const ETL_NOEXCEPT + { + return find(key) != end(); + } + + //************************************************************************* + ///\brief Counts the numbeer elements with key. + ///\param key The key of the element to count. + ///\return 0 or 1 + //************************************************************************* + ETL_CONSTEXPR14 size_type count(const key_type& key) const ETL_NOEXCEPT + { + return contains(key) ? 1 : 0; + } + + //************************************************************************* + ///\brief Counts the numbeer elements with key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element to count. + ///\return 0 or 1 + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 size_type count(const K& key) const ETL_NOEXCEPT + { + return contains(key) ? 1 : 0; + } + + //************************************************************************* + ///\brief Returns a range containing all elements with the key. + /// The range is defined by a pair of two iterators, one to the + /// first element that is not less than the key and second to the first + /// element greater than the key. + ///\param key The key of the element + ///\return etl::pair or std::pair containing a pair of iterators. + //************************************************************************* + ETL_CONSTEXPR14 ETL_OR_STD::pair equal_range(const key_type& key) const ETL_NOEXCEPT + { + return etl::equal_range(begin(), end(), key, vcompare); + } + + //************************************************************************* + ///\brief Returns a range containing all elements with the key. + /// The range is defined by a pair of two iterators, one to the + /// first element that is not less than the key and second to the first + /// element greater than the key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element + ///\return etl::pair or std::pair containing a pair of iterators. + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 ETL_OR_STD::pair equal_range(const K& key) const ETL_NOEXCEPT + { + return etl::equal_range(begin(), end(), key, vcompare); + } + + //************************************************************************* + ///\brief Returns a const_iterator to the first element that is not less than the key. + /// Returns a const_iterator to the first element that is not less than the key. + ///\param key The key of the element + ///\return const_iterator to the element or end() + //************************************************************************* + ETL_CONSTEXPR14 const_iterator lower_bound(const key_type& key) const ETL_NOEXCEPT + { + return etl::lower_bound(begin(), end(), key, vcompare); + } + + //************************************************************************* + ///\brief Returns a const_iterator to the first element that is not less than the key. + /// Returns a const_iterator to the first element that is not less than the key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element + ///\return const_iterator to the element or end() + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 const_iterator lower_bound(const K& key) const ETL_NOEXCEPT + { + return etl::lower_bound(begin(), end(), key, vcompare); + } + + //************************************************************************* + ///\brief Returns a const_iterator to the first element that is greater than the key. + /// Returns a const_iterator to the first element that is greater than the key. + ///\param key The key of the element + ///\return const_iterator to the element or end() + //************************************************************************* + ETL_CONSTEXPR14 const_iterator upper_bound(const key_type& key) const ETL_NOEXCEPT + { + return etl::upper_bound(begin(), end(), key, vcompare); + } + + //************************************************************************* + ///\brief Returns a const_iterator to the first element that is greater than the key. + /// Returns a const_iterator to the first element that is greater than the key. + /// Enabled if the comparator is transparent. + ///\param key The key of the element + ///\return const_iterator to the element or end() + //************************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 const_iterator upper_bound(const K& key) const ETL_NOEXCEPT + { + return etl::upper_bound(begin(), end(), key, vcompare); + } + + //************************************************************************* + /// Checks if the set is empty. + ///\return true if the set is empty. + //************************************************************************* + ETL_CONSTEXPR14 size_type empty() const ETL_NOEXCEPT + { + return size() == 0U; + } + + //************************************************************************* + /// Checks if the set is full. + ///\return true if the set is full. + //************************************************************************* + ETL_CONSTEXPR14 size_type full() const ETL_NOEXCEPT + { + return (max_elements != 0) && (size() == max_elements); + } + + //************************************************************************* + /// Gets the size of the set. + ///\return The size of the set. + //************************************************************************* + ETL_CONSTEXPR14 size_type size() const ETL_NOEXCEPT + { + return size_type(element_list_end - element_list); + } + + //************************************************************************* + /// Gets the maximum size of the set. + ///\return The maximum size of the set. + //************************************************************************* + ETL_CONSTEXPR14 size_type max_size() const ETL_NOEXCEPT + { + return max_elements; + } + + //************************************************************************* + /// Gets the capacity of the set. + /// This is always equal to max_size(). + ///\return The capacity of the set. + //************************************************************************* + ETL_CONSTEXPR14 size_type capacity() const ETL_NOEXCEPT + { + return max_elements; + } + + //************************************************************************* + /// How to compare two key elements. + ///\return An instance of the key_compare type. + //************************************************************************* + ETL_CONSTEXPR14 key_compare key_comp() const ETL_NOEXCEPT + { + return key_compare(); + } + + //************************************************************************* + /// How to compare two value elements. + ///\return An instance of the value_compare type. + //************************************************************************* + ETL_CONSTEXPR14 value_compare value_comp() const ETL_NOEXCEPT + { + return value_compare(); + } + + protected: + + //************************************************************************* + /// Constructor + //************************************************************************* + template + ETL_CONSTEXPR14 explicit iconst_set(const value_type* element_list_, size_type size_, size_type max_elements_) ETL_NOEXCEPT + : element_list(element_list_) + , element_list_end{element_list_ + size_} + , max_elements(max_elements_) + { + } + + private: + + //********************************************************************* + /// Check to see if the keys are equal. + //********************************************************************* + ETL_CONSTEXPR14 bool keys_are_equal(const_reference key1, const_reference key2) const ETL_NOEXCEPT + { + return !key_compare()(key1, key2) && !key_compare()(key2, key1); + } + + //********************************************************************* + /// Check to see if the keys are equal. + /// Enabled if the comparator is transparent. + //********************************************************************* + template ::value, int> = 0> + ETL_CONSTEXPR14 bool keys_are_equal(const K1& key1, const K2& key2) const ETL_NOEXCEPT + { + return !key_compare()(key1, key2) && !key_compare()(key2, key1); + } + + key_compare kcompare; + value_compare vcompare; + + const value_type* element_list; + const value_type* element_list_end; + size_type max_elements; + }; + + //********************************************************************* + /// Map type designed for constexpr. + //********************************************************************* + template > + class const_set : public iconst_set + { + public: + + using base_t = iconst_set; + + using key_type = typename base_t::key_type; + using value_type = typename base_t::value_type; + using key_compare = typename base_t::key_compare; + using const_reference = typename base_t::const_reference; + using const_pointer = typename base_t::const_pointer; + using const_iterator = typename base_t::const_iterator; + using size_type = typename base_t::size_type; + + /// Defines the parameter types + using const_key_reference = const key_type&; + + static_assert((etl::is_default_constructible::value), "key_type must be default constructible"); + + //************************************************************************* + ///\brief Construct a const_set from a variadic list of elements. + /// Static asserts if the elements are not of type value_type. + /// Static asserts if the number of elements is greater than the capacity of the const_set. + //************************************************************************* + template + ETL_CONSTEXPR14 explicit const_set(TElements&&... elements) ETL_NOEXCEPT + : iconst_set(element_list, sizeof...(elements), Size) + , element_list{etl::forward(elements)...} + { + static_assert((etl::are_all_same...>::value), "All elements must be key_type"); + static_assert(sizeof...(elements) <= Size, "Number of elements exceeds capacity"); + } + + private: + + value_type element_list[Size]; + }; + + //************************************************************************* + /// Template deduction guides. + //************************************************************************* +#if ETL_USING_CPP17 + template + const_set(TElements...) -> const_set, sizeof...(TElements)>; +#endif + + //********************************************************************* + /// Map type designed for constexpr. + //********************************************************************* + template > + class const_set_ext : public iconst_set + { + public: + + using base_t = iconst_set; + + using key_type = typename base_t::key_type; + using value_type = typename base_t::value_type; + using key_compare = typename base_t::key_compare; + using const_reference = typename base_t::const_reference; + using const_pointer = typename base_t::const_pointer; + using const_iterator = typename base_t::const_iterator; + using size_type = typename base_t::size_type; + + /// Defines the parameter types + using const_reference = const key_type&; + + static_assert((etl::is_default_constructible::value), "key_type must be default constructible"); + + //************************************************************************* + ///\brief Default construct a const_set. + //************************************************************************* + ETL_CONSTEXPR14 const_set_ext() ETL_NOEXCEPT + : iconst_set(nullptr, 0, 0) + { + } + + //************************************************************************* + ///\brief Construct a const_set from a variadic list of elements. + //************************************************************************* + template + ETL_CONSTEXPR14 explicit const_set_ext(const etl::span& sp) ETL_NOEXCEPT + : iconst_set(sp.data(), Size, Size) + { + } + + //************************************************************************* + ///\brief Construct a const_set from an array. + //************************************************************************* + template + ETL_CONSTEXPR14 explicit const_set_ext(const value_type(&begin_)[Size]) ETL_NOEXCEPT + : iconst_set(begin_, Size, Size) + { + } + }; + + //************************************************************************* + /// Template deduction guides. + //************************************************************************* +#if ETL_USING_CPP17 + template + const_set_ext(const etl::span&) -> const_set_ext; + + template + const_set_ext(const TElements(&)[N]) -> const_set_ext; +#endif + + //************************************************************************* + /// Equality test. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator ==(const etl::iconst_set& lhs, + const etl::iconst_set& rhs) ETL_NOEXCEPT + { + return (lhs.size() == rhs.size()) && etl::equal(lhs.begin(), lhs.end(), rhs.begin()); + } + + //************************************************************************* + /// Inequality test. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator !=(const etl::iconst_set& lhs, + const etl::iconst_set& rhs) ETL_NOEXCEPT + { + return !(lhs == rhs); + } + + //************************************************************************* + /// Less-than. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator <(const etl::iconst_set& lhs, + const etl::iconst_set& rhs) ETL_NOEXCEPT + { + return etl::lexicographical_compare(lhs.begin(), lhs.end(), + rhs.begin(), rhs.end(), + lhs.value_comp()); + } + + //************************************************************************* + /// Greater-than. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator >(const etl::iconst_set& lhs, + const etl::iconst_set& rhs) ETL_NOEXCEPT + { + return (rhs < lhs); + } + + //************************************************************************* + /// Less-than-equal. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator <=(const etl::iconst_set& lhs, + const etl::iconst_set& rhs) ETL_NOEXCEPT + { + return !(rhs < lhs); + } + + //************************************************************************* + /// Greater-than-equal. + //************************************************************************* + template + ETL_CONSTEXPR14 bool operator >=(const etl::iconst_set& lhs, + const etl::iconst_set& rhs) ETL_NOEXCEPT + { + return !(lhs < rhs); + } +} + +#endif diff --git a/include/etl/crc.h b/include/etl/crc.h index 78ceb552..bc3184ac 100644 --- a/include/etl/crc.h +++ b/include/etl/crc.h @@ -45,6 +45,7 @@ SOFTWARE. #include "crc8_maxim.h" #include "crc8_rohc.h" #include "crc8_wcdma.h" +#include "crc8_nrsc5.h" #include "crc16.h" #include "crc16_a.h" diff --git a/include/etl/crc8_nrsc5.h b/include/etl/crc8_nrsc5.h new file mode 100644 index 00000000..aac22e38 --- /dev/null +++ b/include/etl/crc8_nrsc5.h @@ -0,0 +1,76 @@ +///\file + +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2021 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#ifndef ETL_CRC8_NRSC5_INCLUDED +#define ETL_CRC8_NRSC5_INCLUDED + +#include "platform.h" +#include "private/crc_implementation.h" + +namespace etl +{ +#if ETL_USING_CPP11 && !defined(ETL_CRC_FORCE_CPP03_IMPLEMENTATION) + template + using crc8_nrsc5_t = etl::crc_type; +#else + template + class crc8_nrsc5_t : public etl::crc_type + { + public: + + //************************************************************************* + /// Default constructor. + //************************************************************************* + crc8_nrsc5_t() + { + this->reset(); + } + + //************************************************************************* + /// Constructor from range. + /// \param begin Start of the range. + /// \param end End of the range. + //************************************************************************* + template + crc8_nrsc5_t(TIterator begin, const TIterator end) + { + this->reset(); + this->add(begin, end); + } + }; +#endif + + typedef crc8_nrsc5_t<256U> crc8_nrsc5_t256; + typedef crc8_nrsc5_t<16U> crc8_nrsc5_t16; + typedef crc8_nrsc5_t<4U> crc8_nrsc5_t4; + typedef crc8_nrsc5_t256 crc8_nrsc5; +} + +#endif diff --git a/include/etl/private/crc_parameters.h b/include/etl/private/crc_parameters.h index 705684c0..26f2f23c 100644 --- a/include/etl/private/crc_parameters.h +++ b/include/etl/private/crc_parameters.h @@ -81,6 +81,7 @@ namespace etl typedef crc_parameters crc8_wcdma_parameters; typedef crc_parameters crc8_j1850_parameters; typedef crc_parameters crc8_j1850_zero_parameters; + typedef crc_parameters crc8_nrsc5_parameters; // 16 bit. typedef crc_parameters crc16_parameters; diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index 76e06127..1312cf70 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -139,8 +139,10 @@ add_executable(etl_tests test_crc8_j1850.cpp test_crc8_j1850_zero.cpp test_crc8_maxim.cpp + test_crc8_nrsc5.cpp test_crc8_rohc.cpp test_crc8_wcdma.cpp + test_crc8_nrsc5.cpp test_cyclic_value.cpp test_debounce.cpp test_delegate.cpp @@ -364,9 +366,11 @@ elseif (ETL_CXX_STANDARD MATCHES "17") elseif (ETL_CXX_STANDARD MATCHES "20") message(STATUS "Compiling for C++20") set_property(TARGET etl_tests PROPERTY CXX_STANDARD 20) -else() +elseif (ETL_CXX_STANDARD MATCHES "23") message(STATUS "Compiling for C++23") set_property(TARGET etl_tests PROPERTY CXX_STANDARD 23) +else() + message(STATUS "Unsupported C++ standard") endif() if (NO_STL OR ETL_NO_STL) @@ -392,7 +396,7 @@ if (ETL_MESSAGES_ARE_NOT_VIRTUAL) endif() if (ETL_FORCE_TEST_CPP03_IMPLEMENTATION) - message(STATUS "Compiling for C++03 tests") + message(STATUS "Compiling for forced C++03 tests") target_compile_definitions(etl_tests PRIVATE -DETL_FORCE_TEST_CPP03_IMPLEMENTATION) endif() diff --git a/test/test_const_map.cpp b/test/test_const_map.cpp index 19fb9980..65efe5b4 100644 --- a/test/test_const_map.cpp +++ b/test/test_const_map.cpp @@ -5,7 +5,7 @@ Embedded Template Library. https://github.com/ETLCPP/etl https://www.etlcpp.com -Copyright(c) 2025 John Wellbelove, rlindeman +Copyright(c) 2025 John Wellbelove Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files(the 'Software'), to deal @@ -84,7 +84,7 @@ namespace return (lhs < rhs.k); } - // Greater-than operator for char > Key + // Equality operator for Key == Key constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept { return (lhs.k == rhs.k); @@ -93,13 +93,17 @@ namespace #define TEST_GREATER_THAN #ifdef TEST_GREATER_THAN using Data = etl::const_map>; + using Data2 = etl::const_map>; using IData = etl::iconst_map>; using DataTransparentComparator = etl::const_map>; + using DataTransparentComparator2 = etl::const_map>; using IDataTransparentComparator = etl::iconst_map>; #else using Data = etl::const_map>; + using Data2 = etl::const_map>; using IData = etl::iconst_map>; using DataTransparentComparator = etl::const_map>; + using DataTransparentComparator2 = etl::const_map>; using IDataTransparentComparator = etl::iconst_map>; #endif @@ -1234,11 +1238,16 @@ namespace static const Data data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const Data2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const bool equal12 = (data1 == data2); static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1253,11 +1262,16 @@ namespace static const DataTransparentComparator data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const DataTransparentComparator2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const bool equal12 = (data1 == data2); static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1272,11 +1286,16 @@ namespace static const Data data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const Data2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const bool not_equal12 = (data1 != data2); static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* @@ -1291,11 +1310,17 @@ namespace static const DataTransparentComparator data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const DataTransparentComparator2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + + static const bool not_equal12 = (data1 != data2); static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* diff --git a/test/test_const_map_constexpr.cpp b/test/test_const_map_constexpr.cpp index 43336dfa..eca2b48e 100644 --- a/test/test_const_map_constexpr.cpp +++ b/test/test_const_map_constexpr.cpp @@ -5,7 +5,7 @@ Embedded Template Library. https://github.com/ETLCPP/etl https://www.etlcpp.com -Copyright(c) 2025 John Wellbelove, rlindeman +Copyright(c) 2025 John Wellbelove Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files(the 'Software'), to deal @@ -35,7 +35,6 @@ SOFTWARE. #include #include #include -#include #include "etl/const_map.h" #include "etl/map.h" @@ -87,7 +86,7 @@ namespace return (lhs < rhs.k); } - // Greater-than operator for char > Key + // Equality operator for Key == Key constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept { return (lhs.k == rhs.k); @@ -96,13 +95,17 @@ namespace #define TEST_GREATER_THAN #ifdef TEST_GREATER_THAN using Data = etl::const_map>; + using Data2 = etl::const_map>; using IData = etl::iconst_map>; using DataTransparentComparator = etl::const_map>; + using DataTransparentComparator2 = etl::const_map>; using IDataTransparentComparator = etl::iconst_map>; #else using Data = etl::const_map>; + using Data2 = etl::const_map>; using IData = etl::iconst_map>; using DataTransparentComparator = etl::const_map>; + using DataTransparentComparator2 = etl::const_map>; using IDataTransparentComparator = etl::iconst_map>; #endif @@ -111,7 +114,7 @@ namespace using mapped_type = Data::mapped_type; using const_iterator = Data::const_iterator; - SUITE(test_const_map) + SUITE(test_const_map_constexpr) { //************************************************************************* TEST(test_default_constructor) @@ -1237,11 +1240,16 @@ namespace static constexpr Data data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr Data2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr bool equal12 = (data1 == data2); static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1256,11 +1264,16 @@ namespace static constexpr DataTransparentComparator data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr DataTransparentComparator2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr bool equal12 = (data1 == data2); static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1275,11 +1288,16 @@ namespace static constexpr Data data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr Data2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr bool not_equal12 = (data1 != data2); static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* @@ -1294,11 +1312,17 @@ namespace static constexpr DataTransparentComparator data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr DataTransparentComparator2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + + static constexpr bool not_equal12 = (data1 != data2); static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* diff --git a/test/test_const_map_ext.cpp b/test/test_const_map_ext.cpp index 7bded872..fc3ed33e 100644 --- a/test/test_const_map_ext.cpp +++ b/test/test_const_map_ext.cpp @@ -5,7 +5,7 @@ Embedded Template Library. https://github.com/ETLCPP/etl https://www.etlcpp.com -Copyright(c) 2025 John Wellbelove, rlindeman +Copyright(c) 2025 John Wellbelove Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files(the 'Software'), to deal @@ -83,7 +83,7 @@ namespace return (lhs < rhs.k); } - // Greater-than operator for char > Key + // Equality operator for Key == Key constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept { return (lhs.k == rhs.k); @@ -96,9 +96,9 @@ namespace using DataTransparentComparator = etl::const_map_ext>; using IDataTransparentComparator = etl::iconst_map>; #else - using Data = etl::const_map>; + using Data = etl::const_map_ext>; using IData = etl::iconst_map>; - using DataTransparentComparator = etl::const_map>; + using DataTransparentComparator = etl::const_map_ext>; using IDataTransparentComparator = etl::iconst_map>; #endif @@ -108,7 +108,7 @@ namespace using const_iterator = Data::const_iterator; using span_type = etl::span; - SUITE(test_const_map) + SUITE(test_const_map_ext) { //************************************************************************* TEST(test_default_constructor) @@ -1322,15 +1322,21 @@ namespace static const value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const Data data1{values1}; static const Data data2{values2}; static const Data data3{values3}; + static const Data data4{values4}; static const bool equal12 = (data1 == data2); static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1345,15 +1351,21 @@ namespace static const value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const DataTransparentComparator data1{values1}; static const DataTransparentComparator data2{values2}; static const DataTransparentComparator data3{values3}; + static const DataTransparentComparator data4{values4}; static const bool equal12 = (data1 == data2); static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1368,15 +1380,21 @@ namespace static const value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const Data data1{values1}; static const Data data2{values2}; static const Data data3{values3}; + static const Data data4{values4}; static const bool not_equal12 = (data1 != data2); static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* @@ -1391,15 +1409,21 @@ namespace static const value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const DataTransparentComparator data1{values1}; static const DataTransparentComparator data2{values2}; static const DataTransparentComparator data3{values3}; + static const DataTransparentComparator data4{values4}; static const bool not_equal12 = (data1 != data2); static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* diff --git a/test/test_const_map_ext_constexpr.cpp b/test/test_const_map_ext_constexpr.cpp index 61816dd0..845f9185 100644 --- a/test/test_const_map_ext_constexpr.cpp +++ b/test/test_const_map_ext_constexpr.cpp @@ -5,7 +5,7 @@ Embedded Template Library. https://github.com/ETLCPP/etl https://www.etlcpp.com -Copyright(c) 2025 John Wellbelove, rlindeman +Copyright(c) 2025 John Wellbelove Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files(the 'Software'), to deal @@ -83,7 +83,7 @@ namespace return (lhs < rhs.k); } - // Greater-than operator for char > Key + // Equality operator for Key == Key constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept { return (lhs.k == rhs.k); @@ -96,9 +96,9 @@ namespace using DataTransparentComparator = etl::const_map_ext>; using IDataTransparentComparator = etl::iconst_map>; #else - using Data = etl::const_map>; + using Data = etl::const_map_ext>; using IData = etl::iconst_map>; - using DataTransparentComparator = etl::const_map>; + using DataTransparentComparator = etl::const_map_ext>; using IDataTransparentComparator = etl::iconst_map>; #endif @@ -108,7 +108,7 @@ namespace using const_iterator = Data::const_iterator; using span_type = etl::span; - SUITE(test_const_map) + SUITE(test_const_map_ext_constexpr) { //************************************************************************* TEST(test_default_constructor) @@ -234,7 +234,7 @@ namespace static constexpr Data data{ values }; - static const constexpr IData& idata = data; + static constexpr const IData& idata = data; static constexpr bool is_valid = idata.is_valid(); static constexpr size_t size = idata.size(); @@ -1322,15 +1322,21 @@ namespace static constexpr value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr Data data1{values1}; static constexpr Data data2{values2}; static constexpr Data data3{values3}; + static constexpr Data data4{values4}; static constexpr bool equal12 = (data1 == data2); static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1345,15 +1351,21 @@ namespace static constexpr value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr DataTransparentComparator data1{values1}; static constexpr DataTransparentComparator data2{values2}; static constexpr DataTransparentComparator data3{values3}; + static constexpr DataTransparentComparator data4{values4}; static constexpr bool equal12 = (data1 == data2); static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1368,15 +1380,21 @@ namespace static constexpr value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr Data data1{values1}; static constexpr Data data2{values2}; static constexpr Data data3{values3}; + static constexpr Data data4{values4}; static constexpr bool not_equal12 = (data1 != data2); static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* @@ -1391,15 +1409,21 @@ namespace static constexpr value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr DataTransparentComparator data1{values1}; static constexpr DataTransparentComparator data2{values2}; static constexpr DataTransparentComparator data3{values3}; + static constexpr DataTransparentComparator data4{values4}; static constexpr bool not_equal12 = (data1 != data2); static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* diff --git a/test/test_const_multimap.cpp b/test/test_const_multimap.cpp index de9a1089..46457b41 100644 --- a/test/test_const_multimap.cpp +++ b/test/test_const_multimap.cpp @@ -5,7 +5,7 @@ Embedded Template Library. https://github.com/ETLCPP/etl https://www.etlcpp.com -Copyright(c) 2025 John Wellbelove, rlindeman +Copyright(c) 2025 John Wellbelove Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files(the 'Software'), to deal @@ -83,7 +83,7 @@ namespace return (lhs < rhs.k); } - // Greater-than operator for char > Key + // Equality operator for Key == Key constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept { return (lhs.k == rhs.k); @@ -92,13 +92,17 @@ namespace #define TEST_GREATER_THAN #ifdef TEST_GREATER_THAN using Data = etl::const_multimap>; + using Data2 = etl::const_multimap>; using IData = etl::iconst_multimap>; using DataTransparentComparator = etl::const_multimap>; + using DataTransparentComparator2 = etl::const_multimap>; using IDataTransparentComparator = etl::iconst_multimap>; #else using Data = etl::const_multimap>; + using Data2 = etl::const_multimap>; using IData = etl::iconst_multimap>; using DataTransparentComparator = etl::const_multimap>; + using DataTransparentComparator2 = etl::const_multimap>; using IDataTransparentComparator = etl::iconst_multimap>; #endif @@ -970,6 +974,54 @@ namespace #endif } + //************************************************************************* + TEST(test_equal) + { + static const Data data1{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 7 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + + static const Data data2{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 7 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + + static const Data data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + + static const Data2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + + static const bool equal12 = (data1 == data2); + static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_equal_with_transparent_comparator) + { + static const DataTransparentComparator data1{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 7 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + + static const DataTransparentComparator data2{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 7 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + + static const DataTransparentComparator data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + + static const DataTransparentComparator2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + + static const bool equal12 = (data1 == data2); + static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + //************************************************************************* TEST(test_not_equal) { @@ -982,11 +1034,16 @@ namespace static const Data data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const Data2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const bool not_equal12 = (data1 != data2); static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* @@ -1001,11 +1058,16 @@ namespace static const DataTransparentComparator data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const DataTransparentComparator2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const bool not_equal12 = (data1 != data2); static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* diff --git a/test/test_const_multimap_constexpr.cpp b/test/test_const_multimap_constexpr.cpp index 68720992..a881c491 100644 --- a/test/test_const_multimap_constexpr.cpp +++ b/test/test_const_multimap_constexpr.cpp @@ -5,7 +5,7 @@ Embedded Template Library. https://github.com/ETLCPP/etl https://www.etlcpp.com -Copyright(c) 2025 John Wellbelove, rlindeman +Copyright(c) 2025 John Wellbelove Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files(the 'Software'), to deal @@ -85,7 +85,7 @@ namespace return (lhs < rhs.k); } - // Greater-than operator for char > Key + // Equality operator for Key == Key constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept { return (lhs.k == rhs.k); @@ -94,13 +94,17 @@ namespace #define TEST_GREATER_THAN #ifdef TEST_GREATER_THAN using Data = etl::const_multimap>; + using Data2 = etl::const_multimap>; using IData = etl::iconst_multimap>; using DataTransparentComparator = etl::const_multimap>; + using DataTransparentComparator2 = etl::const_multimap>; using IDataTransparentComparator = etl::iconst_multimap>; #else using Data = etl::const_multimap>; + using Data2 = etl::const_multimap>; using IData = etl::iconst_multimap>; using DataTransparentComparator = etl::const_multimap>; + using DataTransparentComparator2 = etl::const_multimap>; using IDataTransparentComparator = etl::iconst_multimap>; #endif @@ -109,7 +113,7 @@ namespace using mapped_type = Data::mapped_type; using const_iterator = Data::const_iterator; - SUITE(test_const_multimap) + SUITE(test_const_multimap_constexpr) { //************************************************************************* TEST(test_default_constructor) @@ -915,11 +919,16 @@ namespace static constexpr Data data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr Data2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr bool equal12 = (data1 == data2); static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -934,11 +943,16 @@ namespace static constexpr DataTransparentComparator data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr DataTransparentComparator2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr bool equal12 = (data1 == data2); static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -953,11 +967,16 @@ namespace static constexpr Data data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr Data2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr bool not_equal12 = (data1 != data2); static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* @@ -972,11 +991,16 @@ namespace static constexpr DataTransparentComparator data3{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr DataTransparentComparator2 data4{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr bool not_equal12 = (data1 != data2); static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* diff --git a/test/test_const_multimap_ext.cpp b/test/test_const_multimap_ext.cpp index b01e475c..b68ad450 100644 --- a/test/test_const_multimap_ext.cpp +++ b/test/test_const_multimap_ext.cpp @@ -5,7 +5,7 @@ Embedded Template Library. https://github.com/ETLCPP/etl https://www.etlcpp.com -Copyright(c) 2025 John Wellbelove, rlindeman +Copyright(c) 2025 John Wellbelove Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files(the 'Software'), to deal @@ -83,7 +83,7 @@ namespace return (lhs < rhs.k); } - // Greater-than operator for char > Key + // Equality operator for Key == Key constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept { return (lhs.k == rhs.k); @@ -98,7 +98,7 @@ namespace #else using Data = etl::const_multimap_ext>; using IData = etl::iconst_multimap>; - using DataTransparentComparator = etl::const_multimap_ext>; + using DataTransparentComparator = etl::const_multimap_ext>; using IDataTransparentComparator = etl::iconst_multimap>; #endif @@ -108,7 +108,7 @@ namespace using const_iterator = Data::const_iterator; using span_type = etl::span; - SUITE(test_const_multimap) + SUITE(test_const_multimap_ext) { //************************************************************************* TEST(test_default_constructor) @@ -1128,15 +1128,21 @@ namespace static const value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const Data data1{values1}; static const Data data2{values2}; static const Data data3{values3}; + static const Data data4{values4}; static const bool equal12 = (data1 == data2); static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1151,15 +1157,21 @@ namespace static const value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const DataTransparentComparator data1{values1}; static const DataTransparentComparator data2{values2}; static const DataTransparentComparator data3{values3}; + static const DataTransparentComparator data4{values4}; static const bool equal12 = (data1 == data2); static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1174,15 +1186,21 @@ namespace static const value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static const Data data1{values1}; static const Data data2{values2}; static const Data data3{values3}; + static const Data data4{values4}; static const bool not_equal12 = (data1 != data2); static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* @@ -1197,15 +1215,22 @@ namespace static const value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static const value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + + static const DataTransparentComparator data1{values1}; static const DataTransparentComparator data2{values2}; static const DataTransparentComparator data3{values3}; + static const DataTransparentComparator data4{values4}; static const bool not_equal12 = (data1 != data2); static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* diff --git a/test/test_const_multimap_ext_constexpr.cpp b/test/test_const_multimap_ext_constexpr.cpp index 3f84174a..0c059c90 100644 --- a/test/test_const_multimap_ext_constexpr.cpp +++ b/test/test_const_multimap_ext_constexpr.cpp @@ -5,7 +5,7 @@ Embedded Template Library. https://github.com/ETLCPP/etl https://www.etlcpp.com -Copyright(c) 2025 John Wellbelove, rlindeman +Copyright(c) 2025 John Wellbelove Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files(the 'Software'), to deal @@ -83,7 +83,7 @@ namespace return (lhs < rhs.k); } - // Greater-than operator for char > Key + // Equality operator for Key == Key constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept { return (lhs.k == rhs.k); @@ -98,7 +98,7 @@ namespace #else using Data = etl::const_multimap_ext>; using IData = etl::iconst_multimap>; - using DataTransparentComparator = etl::const_multimap_ext>; + using DataTransparentComparator = etl::const_multimap_ext>; using IDataTransparentComparator = etl::iconst_multimap>; #endif @@ -108,7 +108,7 @@ namespace using const_iterator = Data::const_iterator; using span_type = etl::span; - SUITE(test_const_multimap) + SUITE(test_const_multimap_ext_constexpr) { //************************************************************************* TEST(test_default_constructor) @@ -162,24 +162,24 @@ namespace TEST(test_constructor_max_size_from_span) { #ifdef TEST_GREATER_THAN - static const value_type values[]{ value_type{Key('J'), 9 }, value_type{Key('I'), 8 }, value_type{Key('H'), 7 }, value_type{Key('G'), 6 }, value_type{Key('F'), 5 }, - value_type{Key('E'), 4 }, value_type{Key('D'), 3 }, value_type{Key('C'), 2 }, value_type{Key('B'), 1 }, value_type{Key('A'), 0 } }; + static constexpr value_type values[]{ value_type{Key('J'), 9 }, value_type{Key('I'), 8 }, value_type{Key('H'), 7 }, value_type{Key('G'), 6 }, value_type{Key('F'), 5 }, + value_type{Key('E'), 4 }, value_type{Key('D'), 3 }, value_type{Key('C'), 2 }, value_type{Key('B'), 1 }, value_type{Key('A'), 0 } }; #else - static const value_type values[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, - value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 7 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr value_type values[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 7 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; #endif - static const span_type span(values); - static const Data data{ span }; + static constexpr span_type span(values); + static constexpr Data data{ span }; - static const bool is_valid = data.is_valid(); - static const size_t size = data.size(); - static const bool empty = data.empty(); - static const bool full = data.full(); - static const size_t capacity = data.capacity(); - static const size_t max_size = data.max_size(); - static const const_iterator begin = data.begin(); - static const const_iterator end = data.end(); + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); CHECK_TRUE(is_valid); CHECK_TRUE(size == Max_Size); @@ -190,6 +190,7 @@ namespace CHECK_FALSE(begin == end); } +#if ETL_USING_CPP17 //************************************************************************* TEST(test_cpp17_deduced_constructor_from_span) { @@ -229,6 +230,7 @@ namespace CHECK_TRUE(data.max_size() == Max_Size); CHECK_FALSE(data.begin() == data.end()); } +#endif //************************************************************************* TEST(test_constructor_min_size) @@ -1117,15 +1119,21 @@ namespace static constexpr value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr Data data1{values1}; static constexpr Data data2{values2}; static constexpr Data data3{values3}; + static constexpr Data data4{values4}; static constexpr bool equal12 = (data1 == data2); static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1140,15 +1148,21 @@ namespace static constexpr value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr DataTransparentComparator data1{values1}; static constexpr DataTransparentComparator data2{values2}; static constexpr DataTransparentComparator data3{values3}; + static constexpr DataTransparentComparator data4{values4}; static constexpr bool equal12 = (data1 == data2); static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); CHECK_TRUE(equal12); CHECK_FALSE(equal13); + CHECK_FALSE(equal14); } //************************************************************************* @@ -1163,15 +1177,21 @@ namespace static constexpr value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + static constexpr Data data1{values1}; static constexpr Data data2{values2}; static constexpr Data data3{values3}; + static constexpr Data data4{values4}; static constexpr bool not_equal12 = (data1 != data2); static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* @@ -1186,15 +1206,22 @@ namespace static constexpr value_type values3[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 } }; + static constexpr value_type values4[]{ value_type{Key('A'), 0 }, value_type{Key('B'), 1 }, value_type{Key('C'), 2 }, value_type{Key('D'), 3 }, value_type{Key('E'), 4 }, + value_type{Key('F'), 5 }, value_type{Key('G'), 6 }, value_type{Key('H'), 6 }, value_type{Key('I'), 8 }, value_type{Key('J'), 9 }, value_type{Key('K'), 10 } }; + + static constexpr DataTransparentComparator data1{values1}; static constexpr DataTransparentComparator data2{values2}; static constexpr DataTransparentComparator data3{values3}; + static constexpr DataTransparentComparator data4{values4}; static constexpr bool not_equal12 = (data1 != data2); static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); CHECK_FALSE(not_equal12); CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); } //************************************************************************* diff --git a/test/test_const_multiset.cpp b/test/test_const_multiset.cpp new file mode 100644 index 00000000..ae97994b --- /dev/null +++ b/test/test_const_multiset.cpp @@ -0,0 +1,1326 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2025 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the 'Software'), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "unit_test_framework.h" + +#include +#include +#include +#include + +#include "etl/const_multiset.h" + +#include "data.h" + +namespace +{ + static const size_t Max_Size = 10UL; + + //************************************************************************* + // The key type + //************************************************************************* + struct Key + { + // Default constructor + constexpr Key() + : k(0) + { + } + + // Construct from char key + constexpr explicit Key(char k_) + : k(k_) + { + } + + char k; + }; + + // Less-than operator for Key < Key + constexpr bool operator <(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k < rhs.k); + } + + // Less-than operator for Key < char + constexpr bool operator <(const Key& lhs, char rhs) noexcept + { + return (lhs.k < rhs); + } + + // Less-than operator for char < Key + constexpr bool operator <(char lhs, const Key& rhs) noexcept + { + return (lhs < rhs.k); + } + + // Equality operator for Key == Key + constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k == rhs.k); + } + + // Equality operator for Key != Key + constexpr bool operator !=(const Key& lhs, const Key& rhs) noexcept + { + return !(lhs.k == rhs.k); + } + +#define TEST_GREATER_THAN +#ifdef TEST_GREATER_THAN + using Data = etl::const_multiset>; + using Data2 = etl::const_multiset>; + using IData = etl::iconst_multiset>; + using DataTransparentComparator = etl::const_multiset>; + using DataTransparentComparator2 = etl::const_multiset>; + using IDataTransparentComparator = etl::iconst_multiset>; +#else + using Data = etl::const_multiset>; + using Data2 = etl::const_multiset>; + using IData = etl::iconst_multiset>; + using DataTransparentComparator = etl::const_multiset>; + using DataTransparentComparator2 = etl::const_multiset>; + using IDataTransparentComparator = etl::iconst_multiset>; +#endif + + using value_type = Data::value_type; + using key_type = Data::key_type; + using const_iterator = Data::const_iterator; + + SUITE(test_const_multiset) + { + //************************************************************************* + TEST(test_default_constructor) + { + static const Data data; + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 0UL); + CHECK_TRUE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_TRUE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_min_size) + { + static const Data data{ Key('A') }; + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 1U); + CHECK_FALSE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + // Enable to check static_assert "Number of elements exceeds capacity" + //************************************************************************* + //TEST(test_constructor_excess_size) + //{ + // static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + // Key('F'), Key('G'), value_type{Key('G')), 7 }, Key('G'), Key('J'), + // Key('K') }; + //} + +#if ETL_USING_CPP17 + //************************************************************************* + TEST(test_cpp17_deduced_constructor) + { + static const etl::const_multiset data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; + + etl::const_multiset check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } +#endif + + //************************************************************************* + TEST(test_begin_const) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + CHECK_TRUE(data.is_valid()); + static const auto value = *data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(Key('J') == value); +#else + CHECK_TRUE(Key('A') == value); +#endif + } + + //************************************************************************* + TEST(test_end_const) + { + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; + + static const const_iterator end_itr = data.end(); + + CHECK_TRUE(end_itr == (data.begin() + data.size())); + } + + //************************************************************************* + TEST(test_equal_range_const) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const ETL_OR_STD::pair resultA = data.equal_range(Key('A')); + static const ETL_OR_STD::pair resultB = data.equal_range(Key('B')); + static const ETL_OR_STD::pair resultC = data.equal_range(Key('C')); + static const ETL_OR_STD::pair resultD = data.equal_range(Key('D')); + static const ETL_OR_STD::pair resultE = data.equal_range(Key('E')); + static const ETL_OR_STD::pair resultF = data.equal_range(Key('F')); + static const ETL_OR_STD::pair resultG = data.equal_range(Key('G')); + static const ETL_OR_STD::pair resultH = data.equal_range(Key('H')); + static const ETL_OR_STD::pair resultI = data.equal_range(Key('I')); + static const ETL_OR_STD::pair resultJ = data.equal_range(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_equal_range_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const ETL_OR_STD::pair resultA = data.equal_range('A'); + static const ETL_OR_STD::pair resultB = data.equal_range('B'); + static const ETL_OR_STD::pair resultC = data.equal_range('C'); + static const ETL_OR_STD::pair resultD = data.equal_range('D'); + static const ETL_OR_STD::pair resultE = data.equal_range('E'); + static const ETL_OR_STD::pair resultF = data.equal_range('F'); + static const ETL_OR_STD::pair resultG = data.equal_range('G'); + static const ETL_OR_STD::pair resultH = data.equal_range('H'); + static const ETL_OR_STD::pair resultI = data.equal_range('I'); + static const ETL_OR_STD::pair resultJ = data.equal_range('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_const) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const const_iterator resultA = data.lower_bound(Key('A')); + static const const_iterator resultB = data.lower_bound(Key('B')); + static const const_iterator resultC = data.lower_bound(Key('C')); + static const const_iterator resultD = data.lower_bound(Key('D')); + static const const_iterator resultE = data.lower_bound(Key('E')); + static const const_iterator resultF = data.lower_bound(Key('F')); + static const const_iterator resultG = data.lower_bound(Key('G')); + static const const_iterator resultH = data.lower_bound(Key('H')); + static const const_iterator resultI = data.lower_bound(Key('I')); + static const const_iterator resultJ = data.lower_bound(Key('J')); + static const const_iterator resultK = data.lower_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const const_iterator resultA = data.lower_bound('A'); + static const const_iterator resultB = data.lower_bound('B'); + static const const_iterator resultC = data.lower_bound('C'); + static const const_iterator resultD = data.lower_bound('D'); + static const const_iterator resultE = data.lower_bound('E'); + static const const_iterator resultF = data.lower_bound('F'); + static const const_iterator resultG = data.lower_bound('G'); + static const const_iterator resultH = data.lower_bound('H'); + static const const_iterator resultI = data.lower_bound('I'); + static const const_iterator resultJ = data.lower_bound('J'); + static const const_iterator resultK = data.lower_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_const) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const const_iterator resultA = data.upper_bound(Key('A')); + static const const_iterator resultB = data.upper_bound(Key('B')); + static const const_iterator resultC = data.upper_bound(Key('C')); + static const const_iterator resultD = data.upper_bound(Key('D')); + static const const_iterator resultE = data.upper_bound(Key('E')); + static const const_iterator resultF = data.upper_bound(Key('F')); + static const const_iterator resultG = data.upper_bound(Key('G')); + static const const_iterator resultH = data.upper_bound(Key('H')); + static const const_iterator resultI = data.upper_bound(Key('I')); + static const const_iterator resultJ = data.upper_bound(Key('J')); + static const const_iterator resultK = data.upper_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const const_iterator resultA = data.upper_bound('A'); + static const const_iterator resultB = data.upper_bound('B'); + static const const_iterator resultC = data.upper_bound('C'); + static const const_iterator resultD = data.upper_bound('D'); + static const const_iterator resultE = data.upper_bound('E'); + static const const_iterator resultF = data.upper_bound('F'); + static const const_iterator resultG = data.upper_bound('G'); + static const const_iterator resultH = data.upper_bound('H'); + static const const_iterator resultI = data.upper_bound('I'); + static const const_iterator resultJ = data.upper_bound('J'); + static const const_iterator resultK = data.upper_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_count_const) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + CHECK_EQUAL(1, data.count(Key('A'))); + CHECK_EQUAL(1, data.count(Key('B'))); + CHECK_EQUAL(1, data.count(Key('C'))); + CHECK_EQUAL(1, data.count(Key('D'))); + CHECK_EQUAL(1, data.count(Key('E'))); + CHECK_EQUAL(1, data.count(Key('F'))); + CHECK_EQUAL(3, data.count(Key('G'))); + CHECK_EQUAL(0, data.count(Key('H'))); + CHECK_EQUAL(0, data.count(Key('I'))); + CHECK_EQUAL(1, data.count(Key('J'))); + CHECK_EQUAL(0, data.count(Key('K'))); + } + + //************************************************************************* + TEST(test_count_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + CHECK_EQUAL(1, data.count('A')); + CHECK_EQUAL(1, data.count('B')); + CHECK_EQUAL(1, data.count('C')); + CHECK_EQUAL(1, data.count('D')); + CHECK_EQUAL(1, data.count('E')); + CHECK_EQUAL(1, data.count('F')); + CHECK_EQUAL(3, data.count('G')); + CHECK_EQUAL(0, data.count('H')); + CHECK_EQUAL(0, data.count('I')); + CHECK_EQUAL(1, data.count('J')); + CHECK_EQUAL(0, data.count('K')); + } + + //************************************************************************* + TEST(test_const_iterator) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + const_iterator itr = data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE(itr == data.end()); +#else + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE(itr == data.end()); +#endif + } + + //************************************************************************* + TEST(test_find_const) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const const_iterator resultA = data.find(Key('A')); + static const const_iterator resultB = data.find(Key('B')); + static const const_iterator resultC = data.find(Key('C')); + static const const_iterator resultD = data.find(Key('D')); + static const const_iterator resultE = data.find(Key('E')); + static const const_iterator resultF = data.find(Key('F')); + static const const_iterator resultG = data.find(Key('G')); + static const const_iterator resultH = data.find(Key('H')); + static const const_iterator resultI = data.find(Key('I')); + static const const_iterator resultJ = data.find(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_find_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const const_iterator resultA = data.find('A'); + static const const_iterator resultB = data.find('B'); + static const const_iterator resultC = data.find('C'); + static const const_iterator resultD = data.find('D'); + static const const_iterator resultE = data.find('E'); + static const const_iterator resultF = data.find('F'); + static const const_iterator resultG = data.find('G'); + static const const_iterator resultH = data.find('H'); + static const const_iterator resultI = data.find('I'); + static const const_iterator resultJ = data.find('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_contains_const) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const bool containsA = data.contains(Key('A')); + static const bool containsB = data.contains(Key('B')); + static const bool containsC = data.contains(Key('C')); + static const bool containsD = data.contains(Key('D')); + static const bool containsE = data.contains(Key('E')); + static const bool containsF = data.contains(Key('F')); + static const bool containsG = data.contains(Key('G')); + static const bool containsH = data.contains(Key('H')); + static const bool containsI = data.contains(Key('I')); + static const bool containsJ = data.contains(Key('J')); + static const bool containsK = data.contains(Key('K')); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_FALSE(containsH); + CHECK_FALSE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_contains_with_transparent_comparator_const) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const bool containsA = data.contains('A'); + static const bool containsB = data.contains('B'); + static const bool containsC = data.contains('C'); + static const bool containsD = data.contains('D'); + static const bool containsE = data.contains('E'); + static const bool containsF = data.contains('F'); + static const bool containsG = data.contains('G'); + static const bool containsH = data.contains('H'); + static const bool containsI = data.contains('I'); + static const bool containsJ = data.contains('J'); + static const bool containsK = data.contains('K'); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_FALSE(containsH); + CHECK_FALSE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_key_comp_const) + { + static const Data data; + static const Data::key_compare compare = data.key_comp(); + + static const bool compareAA = compare(Key{ 'A' }, Key{ 'A' }); + static const bool compareBA = compare(Key{ 'B' }, Key{ 'A' }); + static const bool compareAB = compare(Key{ 'A' }, Key{ 'B' }); + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); + #else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); + #endif + } + + //************************************************************************* + TEST(test_key_comp_const_transparent_comparator) + { + static const DataTransparentComparator data; + static const DataTransparentComparator::key_compare compare = data.key_comp(); + + static const bool compareAA = compare('A', 'A'); + static const bool compareBA = compare('B', 'A'); + static const bool compareAB = compare('A', 'B'); + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); + #else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); + #endif + } + + //************************************************************************* + TEST(test_value_comp_const) + { + static const Data data; + static const Data::value_compare compare = data.value_comp(); + + static const bool compareAA1 = compare(Key('A'), Key('A')); + static const bool compareAA2 = compare(Key('A'), Key{ 'A' }); + static const bool compareAA3 = compare(Key{ 'A' }, Key('A')); + + static const bool compareBA1 = compare(Key('B'), Key('A')); + static const bool compareBA2 = compare(Key('B'), Key{ 'A' }); + static const bool compareBA3 = compare(Key{ 'B' }, Key('A')); + + static const bool compareAB1 = compare(Key('A'), Key('B')); + static const bool compareAB2 = compare(Key('A'), Key{ 'B' }); + static const bool compareAB3 = compare(Key{ 'A' }, Key('B'));; + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); + #else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); + #endif + } + + //************************************************************************* + TEST(test_value_comp_const_transparent_comparator) + { + static const DataTransparentComparator data; + static const DataTransparentComparator::value_compare compare = data.value_comp(); + + static const bool compareAA1 = compare(Key('A'), Key('A')); + static const bool compareAA2 = compare(Key('A'), 'A'); + static const bool compareAA3 = compare('A', Key('A')); + + static const bool compareBA1 = compare(Key('B'), Key('A')); + static const bool compareBA2 = compare(Key('B'), 'A'); + static const bool compareBA3 = compare('B', Key('A')); + + static const bool compareAB1 = compare(Key('A'), Key('B')); + static const bool compareAB2 = compare(Key('A'), 'B'); + static const bool compareAB3 = compare('A', Key('B'));; + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); + #else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); + #endif + } + + //************************************************************************* + TEST(test_equal) + { + static const Data data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const Data2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static const bool equal12 = (data1 == data2); + static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_equal_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const DataTransparentComparator2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static const bool equal12 = (data1 == data2); + static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_not_equal) + { + static const Data data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const Data2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static const bool not_equal12 = (data1 != data2); + static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_not_equal_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const DataTransparentComparator2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static const bool not_equal12 = (data1 != data2); + static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_less_than) + { + static const Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool less_than12 = (data1 < data2); + static const bool less_than23 = (data2 < data3); + static const bool less_than21 = (data2 < data1); + static const bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool less_than12 = (data1 < data2); + static const bool less_than23 = (data2 < data3); + static const bool less_than21 = (data2 < data1); + static const bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal) + { + static const Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool less_than_equal12 = (data1 <= data2); + static const bool less_than_equal23 = (data2 <= data3); + static const bool less_than_equal21 = (data2 <= data1); + static const bool less_than_equal32 = (data3 <= data2); + static const bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool less_than_equal12 = (data1 <= data2); + static const bool less_than_equal23 = (data2 <= data3); + static const bool less_than_equal21 = (data2 <= data1); + static const bool less_than_equal32 = (data3 <= data2); + static const bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than) + { + static const Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool greater_than12 = (data1 > data2); + static const bool greater_than23 = (data2 > data3); + static const bool greater_than21 = (data2 > data1); + static const bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool greater_than12 = (data1 > data2); + static const bool greater_than23 = (data2 > data3); + static const bool greater_than21 = (data2 > data1); + static const bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal) + { + static const Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool greater_than_equal12 = (data1 >= data2); + static const bool greater_than_equal23 = (data2 >= data3); + static const bool greater_than_equal21 = (data2 >= data1); + static const bool greater_than_equal32 = (data3 >= data2); + static const bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool greater_than_equal12 = (data1 >= data2); + static const bool greater_than_equal23 = (data2 >= data3); + static const bool greater_than_equal21 = (data2 >= data1); + static const bool greater_than_equal32 = (data3 >= data2); + static const bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + }; +} diff --git a/test/test_const_multiset_constexpr.cpp b/test/test_const_multiset_constexpr.cpp new file mode 100644 index 00000000..d431466a --- /dev/null +++ b/test/test_const_multiset_constexpr.cpp @@ -0,0 +1,1326 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2025 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the 'Software'), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "unit_test_framework.h" + +#include +#include +#include +#include + +#include "etl/const_multiset.h" + +#include "data.h" + +namespace +{ + static constexpr size_t Max_Size = 10UL; + + //************************************************************************* + // The key type + //************************************************************************* + struct Key + { + // Default constructor + constexpr Key() + : k(0) + { + } + + // Construct from char key + constexpr explicit Key(char k_) + : k(k_) + { + } + + char k; + }; + + // Less-than operator for Key < Key + constexpr bool operator <(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k < rhs.k); + } + + // Less-than operator for Key < char + constexpr bool operator <(const Key& lhs, char rhs) noexcept + { + return (lhs.k < rhs); + } + + // Less-than operator for char < Key + constexpr bool operator <(char lhs, const Key& rhs) noexcept + { + return (lhs < rhs.k); + } + + // Equality operator for Key == Key + constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k == rhs.k); + } + + // Equality operator for Key != Key + constexpr bool operator !=(const Key& lhs, const Key& rhs) noexcept + { + return !(lhs.k == rhs.k); + } + +#define TEST_GREATER_THAN +#ifdef TEST_GREATER_THAN + using Data = etl::const_multiset>; + using Data2 = etl::const_multiset>; + using IData = etl::iconst_multiset>; + using DataTransparentComparator = etl::const_multiset>; + using DataTransparentComparator2 = etl::const_multiset>; + using IDataTransparentComparator = etl::iconst_multiset>; +#else + using Data = etl::const_multiset>; + using Data2 = etl::const_multiset>; + using IData = etl::iconst_multiset>; + using DataTransparentComparator = etl::const_multiset>; + using DataTransparentComparator2 = etl::const_multiset>; + using IDataTransparentComparator = etl::iconst_multiset>; +#endif + + using value_type = Data::value_type; + using key_type = Data::key_type; + using const_iterator = Data::const_iterator; + + SUITE(test_const_multiset_constexpr) + { + //************************************************************************* + TEST(test_default_constructor) + { + static constexpr Data data; + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 0UL); + CHECK_TRUE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_TRUE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_min_size) + { + static constexpr Data data{ Key('A') }; + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 1U); + CHECK_FALSE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + // Enable to check static_assert "Number of elements exceeds capacity" + //************************************************************************* + //TEST(test_constructor_excess_size) + //{ + // static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + // Key('F'), Key('G'), value_type{Key('G')), 7 }, Key('G'), Key('J'), + // Key('K') }; + //} + +#if ETL_USING_CPP17 + //************************************************************************* + TEST(test_cpp17_deduced_constructor) + { + static constexpr etl::const_multiset data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; + + etl::const_multiset check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } +#endif + + //************************************************************************* + TEST(test_begin_const) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + CHECK_TRUE(data.is_valid()); + static constexpr auto value = *data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(Key('J') == value); +#else + CHECK_TRUE(Key('A') == value); +#endif + } + + //************************************************************************* + TEST(test_end_const) + { + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; + + static constexpr const_iterator end_itr = data.end(); + + CHECK_TRUE(end_itr == (data.begin() + data.size())); + } + + //************************************************************************* + TEST(test_equal_range_const) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr ETL_OR_STD::pair resultA = data.equal_range(Key('A')); + static constexpr ETL_OR_STD::pair resultB = data.equal_range(Key('B')); + static constexpr ETL_OR_STD::pair resultC = data.equal_range(Key('C')); + static constexpr ETL_OR_STD::pair resultD = data.equal_range(Key('D')); + static constexpr ETL_OR_STD::pair resultE = data.equal_range(Key('E')); + static constexpr ETL_OR_STD::pair resultF = data.equal_range(Key('F')); + static constexpr ETL_OR_STD::pair resultG = data.equal_range(Key('G')); + static constexpr ETL_OR_STD::pair resultH = data.equal_range(Key('H')); + static constexpr ETL_OR_STD::pair resultI = data.equal_range(Key('I')); + static constexpr ETL_OR_STD::pair resultJ = data.equal_range(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_equal_range_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr ETL_OR_STD::pair resultA = data.equal_range('A'); + static constexpr ETL_OR_STD::pair resultB = data.equal_range('B'); + static constexpr ETL_OR_STD::pair resultC = data.equal_range('C'); + static constexpr ETL_OR_STD::pair resultD = data.equal_range('D'); + static constexpr ETL_OR_STD::pair resultE = data.equal_range('E'); + static constexpr ETL_OR_STD::pair resultF = data.equal_range('F'); + static constexpr ETL_OR_STD::pair resultG = data.equal_range('G'); + static constexpr ETL_OR_STD::pair resultH = data.equal_range('H'); + static constexpr ETL_OR_STD::pair resultI = data.equal_range('I'); + static constexpr ETL_OR_STD::pair resultJ = data.equal_range('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_const) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr const_iterator resultA = data.lower_bound(Key('A')); + static constexpr const_iterator resultB = data.lower_bound(Key('B')); + static constexpr const_iterator resultC = data.lower_bound(Key('C')); + static constexpr const_iterator resultD = data.lower_bound(Key('D')); + static constexpr const_iterator resultE = data.lower_bound(Key('E')); + static constexpr const_iterator resultF = data.lower_bound(Key('F')); + static constexpr const_iterator resultG = data.lower_bound(Key('G')); + static constexpr const_iterator resultH = data.lower_bound(Key('H')); + static constexpr const_iterator resultI = data.lower_bound(Key('I')); + static constexpr const_iterator resultJ = data.lower_bound(Key('J')); + static constexpr const_iterator resultK = data.lower_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr const_iterator resultA = data.lower_bound('A'); + static constexpr const_iterator resultB = data.lower_bound('B'); + static constexpr const_iterator resultC = data.lower_bound('C'); + static constexpr const_iterator resultD = data.lower_bound('D'); + static constexpr const_iterator resultE = data.lower_bound('E'); + static constexpr const_iterator resultF = data.lower_bound('F'); + static constexpr const_iterator resultG = data.lower_bound('G'); + static constexpr const_iterator resultH = data.lower_bound('H'); + static constexpr const_iterator resultI = data.lower_bound('I'); + static constexpr const_iterator resultJ = data.lower_bound('J'); + static constexpr const_iterator resultK = data.lower_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_const) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr const_iterator resultA = data.upper_bound(Key('A')); + static constexpr const_iterator resultB = data.upper_bound(Key('B')); + static constexpr const_iterator resultC = data.upper_bound(Key('C')); + static constexpr const_iterator resultD = data.upper_bound(Key('D')); + static constexpr const_iterator resultE = data.upper_bound(Key('E')); + static constexpr const_iterator resultF = data.upper_bound(Key('F')); + static constexpr const_iterator resultG = data.upper_bound(Key('G')); + static constexpr const_iterator resultH = data.upper_bound(Key('H')); + static constexpr const_iterator resultI = data.upper_bound(Key('I')); + static constexpr const_iterator resultJ = data.upper_bound(Key('J')); + static constexpr const_iterator resultK = data.upper_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr const_iterator resultA = data.upper_bound('A'); + static constexpr const_iterator resultB = data.upper_bound('B'); + static constexpr const_iterator resultC = data.upper_bound('C'); + static constexpr const_iterator resultD = data.upper_bound('D'); + static constexpr const_iterator resultE = data.upper_bound('E'); + static constexpr const_iterator resultF = data.upper_bound('F'); + static constexpr const_iterator resultG = data.upper_bound('G'); + static constexpr const_iterator resultH = data.upper_bound('H'); + static constexpr const_iterator resultI = data.upper_bound('I'); + static constexpr const_iterator resultJ = data.upper_bound('J'); + static constexpr const_iterator resultK = data.upper_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_count_const) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + CHECK_EQUAL(1, data.count(Key('A'))); + CHECK_EQUAL(1, data.count(Key('B'))); + CHECK_EQUAL(1, data.count(Key('C'))); + CHECK_EQUAL(1, data.count(Key('D'))); + CHECK_EQUAL(1, data.count(Key('E'))); + CHECK_EQUAL(1, data.count(Key('F'))); + CHECK_EQUAL(3, data.count(Key('G'))); + CHECK_EQUAL(0, data.count(Key('H'))); + CHECK_EQUAL(0, data.count(Key('I'))); + CHECK_EQUAL(1, data.count(Key('J'))); + CHECK_EQUAL(0, data.count(Key('K'))); + } + + //************************************************************************* + TEST(test_count_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + CHECK_EQUAL(1, data.count('A')); + CHECK_EQUAL(1, data.count('B')); + CHECK_EQUAL(1, data.count('C')); + CHECK_EQUAL(1, data.count('D')); + CHECK_EQUAL(1, data.count('E')); + CHECK_EQUAL(1, data.count('F')); + CHECK_EQUAL(3, data.count('G')); + CHECK_EQUAL(0, data.count('H')); + CHECK_EQUAL(0, data.count('I')); + CHECK_EQUAL(1, data.count('J')); + CHECK_EQUAL(0, data.count('K')); + } + + //************************************************************************* + TEST(test_const_iterator) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + const_iterator itr = data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE(itr == data.end()); +#else + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE(itr == data.end()); +#endif + } + + //************************************************************************* + TEST(test_find_const) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr const_iterator resultA = data.find(Key('A')); + static constexpr const_iterator resultB = data.find(Key('B')); + static constexpr const_iterator resultC = data.find(Key('C')); + static constexpr const_iterator resultD = data.find(Key('D')); + static constexpr const_iterator resultE = data.find(Key('E')); + static constexpr const_iterator resultF = data.find(Key('F')); + static constexpr const_iterator resultG = data.find(Key('G')); + static constexpr const_iterator resultH = data.find(Key('H')); + static constexpr const_iterator resultI = data.find(Key('I')); + static constexpr const_iterator resultJ = data.find(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_find_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr const_iterator resultA = data.find('A'); + static constexpr const_iterator resultB = data.find('B'); + static constexpr const_iterator resultC = data.find('C'); + static constexpr const_iterator resultD = data.find('D'); + static constexpr const_iterator resultE = data.find('E'); + static constexpr const_iterator resultF = data.find('F'); + static constexpr const_iterator resultG = data.find('G'); + static constexpr const_iterator resultH = data.find('H'); + static constexpr const_iterator resultI = data.find('I'); + static constexpr const_iterator resultJ = data.find('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_contains_const) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr bool containsA = data.contains(Key('A')); + static constexpr bool containsB = data.contains(Key('B')); + static constexpr bool containsC = data.contains(Key('C')); + static constexpr bool containsD = data.contains(Key('D')); + static constexpr bool containsE = data.contains(Key('E')); + static constexpr bool containsF = data.contains(Key('F')); + static constexpr bool containsG = data.contains(Key('G')); + static constexpr bool containsH = data.contains(Key('H')); + static constexpr bool containsI = data.contains(Key('I')); + static constexpr bool containsJ = data.contains(Key('J')); + static constexpr bool containsK = data.contains(Key('K')); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_FALSE(containsH); + CHECK_FALSE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_contains_with_transparent_comparator_const) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr bool containsA = data.contains('A'); + static constexpr bool containsB = data.contains('B'); + static constexpr bool containsC = data.contains('C'); + static constexpr bool containsD = data.contains('D'); + static constexpr bool containsE = data.contains('E'); + static constexpr bool containsF = data.contains('F'); + static constexpr bool containsG = data.contains('G'); + static constexpr bool containsH = data.contains('H'); + static constexpr bool containsI = data.contains('I'); + static constexpr bool containsJ = data.contains('J'); + static constexpr bool containsK = data.contains('K'); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_FALSE(containsH); + CHECK_FALSE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_key_comp_const) + { + static constexpr Data data; + static constexpr Data::key_compare compare = data.key_comp(); + + static constexpr bool compareAA = compare(Key{ 'A' }, Key{ 'A' }); + static constexpr bool compareBA = compare(Key{ 'B' }, Key{ 'A' }); + static constexpr bool compareAB = compare(Key{ 'A' }, Key{ 'B' }); + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); + #else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); + #endif + } + + //************************************************************************* + TEST(test_key_comp_const_transparent_comparator) + { + static constexpr DataTransparentComparator data; + static constexpr DataTransparentComparator::key_compare compare = data.key_comp(); + + static constexpr bool compareAA = compare('A', 'A'); + static constexpr bool compareBA = compare('B', 'A'); + static constexpr bool compareAB = compare('A', 'B'); + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); + #else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); + #endif + } + + //************************************************************************* + TEST(test_value_comp_const) + { + static constexpr Data data; + static constexpr Data::value_compare compare = data.value_comp(); + + static constexpr bool compareAA1 = compare(Key('A'), Key('A')); + static constexpr bool compareAA2 = compare(Key('A'), Key{ 'A' }); + static constexpr bool compareAA3 = compare(Key{ 'A' }, Key('A')); + + static constexpr bool compareBA1 = compare(Key('B'), Key('A')); + static constexpr bool compareBA2 = compare(Key('B'), Key{ 'A' }); + static constexpr bool compareBA3 = compare(Key{ 'B' }, Key('A')); + + static constexpr bool compareAB1 = compare(Key('A'), Key('B')); + static constexpr bool compareAB2 = compare(Key('A'), Key{ 'B' }); + static constexpr bool compareAB3 = compare(Key{ 'A' }, Key('B'));; + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); + #else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); + #endif + } + + //************************************************************************* + TEST(test_value_comp_const_transparent_comparator) + { + static constexpr DataTransparentComparator data; + static constexpr DataTransparentComparator::value_compare compare = data.value_comp(); + + static constexpr bool compareAA1 = compare(Key('A'), Key('A')); + static constexpr bool compareAA2 = compare(Key('A'), 'A'); + static constexpr bool compareAA3 = compare('A', Key('A')); + + static constexpr bool compareBA1 = compare(Key('B'), Key('A')); + static constexpr bool compareBA2 = compare(Key('B'), 'A'); + static constexpr bool compareBA3 = compare('B', Key('A')); + + static constexpr bool compareAB1 = compare(Key('A'), Key('B')); + static constexpr bool compareAB2 = compare(Key('A'), 'B'); + static constexpr bool compareAB3 = compare('A', Key('B'));; + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); + #else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); + #endif + } + + //************************************************************************* + TEST(test_equal) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr Data2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static constexpr bool equal12 = (data1 == data2); + static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_equal_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static constexpr bool equal12 = (data1 == data2); + static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_not_equal) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr Data2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static constexpr bool not_equal12 = (data1 != data2); + static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_not_equal_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static constexpr bool not_equal12 = (data1 != data2); + static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_less_than) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool less_than12 = (data1 < data2); + static constexpr bool less_than23 = (data2 < data3); + static constexpr bool less_than21 = (data2 < data1); + static constexpr bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool less_than12 = (data1 < data2); + static constexpr bool less_than23 = (data2 < data3); + static constexpr bool less_than21 = (data2 < data1); + static constexpr bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool less_than_equal12 = (data1 <= data2); + static constexpr bool less_than_equal23 = (data2 <= data3); + static constexpr bool less_than_equal21 = (data2 <= data1); + static constexpr bool less_than_equal32 = (data3 <= data2); + static constexpr bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool less_than_equal12 = (data1 <= data2); + static constexpr bool less_than_equal23 = (data2 <= data3); + static constexpr bool less_than_equal21 = (data2 <= data1); + static constexpr bool less_than_equal32 = (data3 <= data2); + static constexpr bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool greater_than12 = (data1 > data2); + static constexpr bool greater_than23 = (data2 > data3); + static constexpr bool greater_than21 = (data2 > data1); + static constexpr bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool greater_than12 = (data1 > data2); + static constexpr bool greater_than23 = (data2 > data3); + static constexpr bool greater_than21 = (data2 > data1); + static constexpr bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool greater_than_equal12 = (data1 >= data2); + static constexpr bool greater_than_equal23 = (data2 >= data3); + static constexpr bool greater_than_equal21 = (data2 >= data1); + static constexpr bool greater_than_equal32 = (data3 >= data2); + static constexpr bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool greater_than_equal12 = (data1 >= data2); + static constexpr bool greater_than_equal23 = (data2 >= data3); + static constexpr bool greater_than_equal21 = (data2 >= data1); + static constexpr bool greater_than_equal32 = (data3 >= data2); + static constexpr bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + }; +} diff --git a/test/test_const_multiset_ext.cpp b/test/test_const_multiset_ext.cpp new file mode 100644 index 00000000..a05fef54 --- /dev/null +++ b/test/test_const_multiset_ext.cpp @@ -0,0 +1,1423 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2025 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the 'Software'), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "unit_test_framework.h" + +#include +#include +#include +#include + +#include "etl/const_multiset.h" +#include "etl/span.h" + +#include "data.h" + +namespace +{ + static const size_t Max_Size = 10UL; + + //************************************************************************* + // The key type + //************************************************************************* + struct Key + { + // Default constructor + constexpr Key() + : k(0) + { + } + + // Construct from char key + constexpr explicit Key(char k_) + : k(k_) + { + } + + char k; + }; + + // Less-than operator for Key < Key + constexpr bool operator <(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k < rhs.k); + } + + // Less-than operator for Key < char + constexpr bool operator <(const Key& lhs, char rhs) noexcept + { + return (lhs.k < rhs); + } + + // Less-than operator for char < Key + constexpr bool operator <(char lhs, const Key& rhs) noexcept + { + return (lhs < rhs.k); + } + + // Equality operator for Key == Key + constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k == rhs.k); + } + + // Equality operator for Key != Key + constexpr bool operator !=(const Key& lhs, const Key& rhs) noexcept + { + return !(lhs.k == rhs.k); + } + +#define TEST_GREATER_THAN +#ifdef TEST_GREATER_THAN + using Data = etl::const_multiset_ext>; + using IData = etl::iconst_multiset>; + using DataTransparentComparator = etl::const_multiset_ext>; + using IDataTransparentComparator = etl::iconst_multiset>; +#else + using Data = etl::const_multiset_ext>; + using IData = etl::iconst_multiset>; + using DataTransparentComparator = etl::const_multiset_ext>; + using IDataTransparentComparator = etl::iconst_multiset>; +#endif + + using value_type = Data::value_type; + using key_type = Data::key_type; + using const_iterator = Data::const_iterator; + using span_type = etl::span; + + SUITE(test_const_multiset_ext) + { + //************************************************************************* + TEST(test_default_constructor) + { + static const Data data; + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 0UL); + CHECK_TRUE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == 0UL); + CHECK_TRUE(max_size == 0UL); + CHECK_TRUE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_min_size) + { + static const value_type values[]{ Key('A') }; + + static const Data data(values); + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 1U); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == 1U); + CHECK_TRUE(max_size == 1U); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const Data data(values); + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + +#if ETL_USING_CPP17 + //************************************************************************* + TEST(test_cpp17_deduced_constructor_from_span) + { + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const span_type span(values); + static const etl::const_multiset_ext data{span}; + + etl::const_multiset check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } + + //************************************************************************* + TEST(test_cpp17_deduced_constructor_from_array) + { + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const etl::const_multiset_ext data{values}; + + etl::const_multiset check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } +#endif + + //************************************************************************* + TEST(test_begin_const) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const Data data(values); + + CHECK_TRUE(data.is_valid()); + static const auto value = *data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(Key('J') == value); +#else + CHECK_TRUE(Key('A') == value); +#endif + } + + //************************************************************************* + TEST(test_end_const) + { + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; + + static const Data data(values); + + static const const_iterator end_itr = data.end(); + + CHECK_TRUE(end_itr == (data.begin() + data.size())); + } + + //************************************************************************* + TEST(test_equal_range_const) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const Data data(values); + + static const ETL_OR_STD::pair resultA = data.equal_range(Key('A')); + static const ETL_OR_STD::pair resultB = data.equal_range(Key('B')); + static const ETL_OR_STD::pair resultC = data.equal_range(Key('C')); + static const ETL_OR_STD::pair resultD = data.equal_range(Key('D')); + static const ETL_OR_STD::pair resultE = data.equal_range(Key('E')); + static const ETL_OR_STD::pair resultF = data.equal_range(Key('F')); + static const ETL_OR_STD::pair resultG = data.equal_range(Key('G')); + static const ETL_OR_STD::pair resultH = data.equal_range(Key('H')); + static const ETL_OR_STD::pair resultI = data.equal_range(Key('I')); + static const ETL_OR_STD::pair resultJ = data.equal_range(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_equal_range_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const DataTransparentComparator data(values); + + static const ETL_OR_STD::pair resultA = data.equal_range('A'); + static const ETL_OR_STD::pair resultB = data.equal_range('B'); + static const ETL_OR_STD::pair resultC = data.equal_range('C'); + static const ETL_OR_STD::pair resultD = data.equal_range('D'); + static const ETL_OR_STD::pair resultE = data.equal_range('E'); + static const ETL_OR_STD::pair resultF = data.equal_range('F'); + static const ETL_OR_STD::pair resultG = data.equal_range('G'); + static const ETL_OR_STD::pair resultH = data.equal_range('H'); + static const ETL_OR_STD::pair resultI = data.equal_range('I'); + static const ETL_OR_STD::pair resultJ = data.equal_range('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_const) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const Data data(values); + + static const const_iterator resultA = data.lower_bound(Key('A')); + static const const_iterator resultB = data.lower_bound(Key('B')); + static const const_iterator resultC = data.lower_bound(Key('C')); + static const const_iterator resultD = data.lower_bound(Key('D')); + static const const_iterator resultE = data.lower_bound(Key('E')); + static const const_iterator resultF = data.lower_bound(Key('F')); + static const const_iterator resultG = data.lower_bound(Key('G')); + static const const_iterator resultH = data.lower_bound(Key('H')); + static const const_iterator resultI = data.lower_bound(Key('I')); + static const const_iterator resultJ = data.lower_bound(Key('J')); + static const const_iterator resultK = data.lower_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const DataTransparentComparator data(values); + + static const const_iterator resultA = data.lower_bound('A'); + static const const_iterator resultB = data.lower_bound('B'); + static const const_iterator resultC = data.lower_bound('C'); + static const const_iterator resultD = data.lower_bound('D'); + static const const_iterator resultE = data.lower_bound('E'); + static const const_iterator resultF = data.lower_bound('F'); + static const const_iterator resultG = data.lower_bound('G'); + static const const_iterator resultH = data.lower_bound('H'); + static const const_iterator resultI = data.lower_bound('I'); + static const const_iterator resultJ = data.lower_bound('J'); + static const const_iterator resultK = data.lower_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_const) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const Data data(values); + + static const const_iterator resultA = data.upper_bound(Key('A')); + static const const_iterator resultB = data.upper_bound(Key('B')); + static const const_iterator resultC = data.upper_bound(Key('C')); + static const const_iterator resultD = data.upper_bound(Key('D')); + static const const_iterator resultE = data.upper_bound(Key('E')); + static const const_iterator resultF = data.upper_bound(Key('F')); + static const const_iterator resultG = data.upper_bound(Key('G')); + static const const_iterator resultH = data.upper_bound(Key('H')); + static const const_iterator resultI = data.upper_bound(Key('I')); + static const const_iterator resultJ = data.upper_bound(Key('J')); + static const const_iterator resultK = data.upper_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const DataTransparentComparator data(values); + + static const const_iterator resultA = data.upper_bound('A'); + static const const_iterator resultB = data.upper_bound('B'); + static const const_iterator resultC = data.upper_bound('C'); + static const const_iterator resultD = data.upper_bound('D'); + static const const_iterator resultE = data.upper_bound('E'); + static const const_iterator resultF = data.upper_bound('F'); + static const const_iterator resultG = data.upper_bound('G'); + static const const_iterator resultH = data.upper_bound('H'); + static const const_iterator resultI = data.upper_bound('I'); + static const const_iterator resultJ = data.upper_bound('J'); + static const const_iterator resultK = data.upper_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_count_const) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const Data data(values); + + CHECK_EQUAL(1, data.count(Key('A'))); + CHECK_EQUAL(1, data.count(Key('B'))); + CHECK_EQUAL(1, data.count(Key('C'))); + CHECK_EQUAL(1, data.count(Key('D'))); + CHECK_EQUAL(1, data.count(Key('E'))); + CHECK_EQUAL(1, data.count(Key('F'))); + CHECK_EQUAL(3, data.count(Key('G'))); + CHECK_EQUAL(0, data.count(Key('H'))); + CHECK_EQUAL(0, data.count(Key('I'))); + CHECK_EQUAL(1, data.count(Key('J'))); + CHECK_EQUAL(0, data.count(Key('K'))); + } + + //************************************************************************* + TEST(test_count_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const DataTransparentComparator data(values); + + CHECK_EQUAL(1, data.count('A')); + CHECK_EQUAL(1, data.count('B')); + CHECK_EQUAL(1, data.count('C')); + CHECK_EQUAL(1, data.count('D')); + CHECK_EQUAL(1, data.count('E')); + CHECK_EQUAL(1, data.count('F')); + CHECK_EQUAL(3, data.count('G')); + CHECK_EQUAL(0, data.count('H')); + CHECK_EQUAL(0, data.count('I')); + CHECK_EQUAL(1, data.count('J')); + CHECK_EQUAL(0, data.count('K')); + } + + //************************************************************************* + TEST(test_const_iterator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const Data data(values); + + const_iterator itr = data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE(itr == data.end()); +#else + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE(itr == data.end()); +#endif + } + + //************************************************************************* + TEST(test_find_const) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const Data data(values); + + static const const_iterator resultA = data.find(Key('A')); + static const const_iterator resultB = data.find(Key('B')); + static const const_iterator resultC = data.find(Key('C')); + static const const_iterator resultD = data.find(Key('D')); + static const const_iterator resultE = data.find(Key('E')); + static const const_iterator resultF = data.find(Key('F')); + static const const_iterator resultG = data.find(Key('G')); + static const const_iterator resultH = data.find(Key('H')); + static const const_iterator resultI = data.find(Key('I')); + static const const_iterator resultJ = data.find(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_find_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const DataTransparentComparator data(values); + + static const const_iterator resultA = data.find('A'); + static const const_iterator resultB = data.find('B'); + static const const_iterator resultC = data.find('C'); + static const const_iterator resultD = data.find('D'); + static const const_iterator resultE = data.find('E'); + static const const_iterator resultF = data.find('F'); + static const const_iterator resultG = data.find('G'); + static const const_iterator resultH = data.find('H'); + static const const_iterator resultI = data.find('I'); + static const const_iterator resultJ = data.find('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_contains_const) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const Data data(values); + + static const bool containsA = data.contains(Key('A')); + static const bool containsB = data.contains(Key('B')); + static const bool containsC = data.contains(Key('C')); + static const bool containsD = data.contains(Key('D')); + static const bool containsE = data.contains(Key('E')); + static const bool containsF = data.contains(Key('F')); + static const bool containsG = data.contains(Key('G')); + static const bool containsH = data.contains(Key('H')); + static const bool containsI = data.contains(Key('I')); + static const bool containsJ = data.contains(Key('J')); + static const bool containsK = data.contains(Key('K')); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_FALSE(containsH); + CHECK_FALSE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_contains_with_transparent_comparator_const) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static const DataTransparentComparator data(values); + + static const bool containsA = data.contains('A'); + static const bool containsB = data.contains('B'); + static const bool containsC = data.contains('C'); + static const bool containsD = data.contains('D'); + static const bool containsE = data.contains('E'); + static const bool containsF = data.contains('F'); + static const bool containsG = data.contains('G'); + static const bool containsH = data.contains('H'); + static const bool containsI = data.contains('I'); + static const bool containsJ = data.contains('J'); + static const bool containsK = data.contains('K'); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_FALSE(containsH); + CHECK_FALSE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_key_comp_const) + { + static const Data data; + static const Data::key_compare compare = data.key_comp(); + + static const bool compareAA = compare(Key{ 'A' }, Key{ 'A' }); + static const bool compareBA = compare(Key{ 'B' }, Key{ 'A' }); + static const bool compareAB = compare(Key{ 'A' }, Key{ 'B' }); + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); + #else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); + #endif + } + + //************************************************************************* + TEST(test_key_comp_const_transparent_comparator) + { + static const DataTransparentComparator data; + static const DataTransparentComparator::key_compare compare = data.key_comp(); + + static const bool compareAA = compare('A', 'A'); + static const bool compareBA = compare('B', 'A'); + static const bool compareAB = compare('A', 'B'); + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); + #else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); + #endif + } + + //************************************************************************* + TEST(test_value_comp_const) + { + static const Data data; + static const Data::value_compare compare = data.value_comp(); + + static const bool compareAA1 = compare(Key('A'), Key('A')); + static const bool compareAA2 = compare(Key('A'), Key{ 'A' }); + static const bool compareAA3 = compare(Key{ 'A' }, Key('A')); + + static const bool compareBA1 = compare(Key('B'), Key('A')); + static const bool compareBA2 = compare(Key('B'), Key{ 'A' }); + static const bool compareBA3 = compare(Key{ 'B' }, Key('A')); + + static const bool compareAB1 = compare(Key('A'), Key('B')); + static const bool compareAB2 = compare(Key('A'), Key{ 'B' }); + static const bool compareAB3 = compare(Key{ 'A' }, Key('B'));; + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); + #else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); + #endif + } + + //************************************************************************* + TEST(test_value_comp_const_transparent_comparator) + { + static const DataTransparentComparator data; + static const DataTransparentComparator::value_compare compare = data.value_comp(); + + static const bool compareAA1 = compare(Key('A'), Key('A')); + static const bool compareAA2 = compare(Key('A'), 'A'); + static const bool compareAA3 = compare('A', Key('A')); + + static const bool compareBA1 = compare(Key('B'), Key('A')); + static const bool compareBA2 = compare(Key('B'), 'A'); + static const bool compareBA3 = compare('B', Key('A')); + + static const bool compareAB1 = compare(Key('A'), Key('B')); + static const bool compareAB2 = compare(Key('A'), 'B'); + static const bool compareAB3 = compare('A', Key('B'));; + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); + #else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); + #endif + } + + //************************************************************************* + TEST(test_equal) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static const Data data1(values1); + static const Data data2(values2); + static const Data data3(values3); + static const Data data4(values4); + + static const bool equal12 = (data1 == data2); + static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_equal_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static const DataTransparentComparator data1(values1); + static const DataTransparentComparator data2(values2); + static const DataTransparentComparator data3(values3); + static const DataTransparentComparator data4(values4); + + static const bool equal12 = (data1 == data2); + static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_not_equal) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static const Data data1(values1); + static const Data data2(values2); + static const Data data3(values3); + static const Data data4(values4); + + static const bool not_equal12 = (data1 != data2); + static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_not_equal_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static const DataTransparentComparator data1(values1); + static const DataTransparentComparator data2(values2); + static const DataTransparentComparator data3(values3); + static const DataTransparentComparator data4(values4); + + static const bool not_equal12 = (data1 != data2); + static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_less_than) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data1(values1); + static const Data data2(values2); + static const Data data3(values3); + + static const bool less_than12 = (data1 < data2); + static const bool less_than23 = (data2 < data3); + static const bool less_than21 = (data2 < data1); + static const bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data1(values1); + static const DataTransparentComparator data2(values2); + static const DataTransparentComparator data3(values3); + + static const bool less_than12 = (data1 < data2); + static const bool less_than23 = (data2 < data3); + static const bool less_than21 = (data2 < data1); + static const bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data1(values1); + static const Data data2(values2); + static const Data data3(values3); + + static const bool less_than_equal12 = (data1 <= data2); + static const bool less_than_equal23 = (data2 <= data3); + static const bool less_than_equal21 = (data2 <= data1); + static const bool less_than_equal32 = (data3 <= data2); + static const bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data1(values1); + static const DataTransparentComparator data2(values2); + static const DataTransparentComparator data3(values3); + + static const bool less_than_equal12 = (data1 <= data2); + static const bool less_than_equal23 = (data2 <= data3); + static const bool less_than_equal21 = (data2 <= data1); + static const bool less_than_equal32 = (data3 <= data2); + static const bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data1(values1); + static const Data data2(values2); + static const Data data3(values3); + + static const bool greater_than12 = (data1 > data2); + static const bool greater_than23 = (data2 > data3); + static const bool greater_than21 = (data2 > data1); + static const bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data1(values1); + static const DataTransparentComparator data2(values2); + static const DataTransparentComparator data3(values3); + + static const bool greater_than12 = (data1 > data2); + static const bool greater_than23 = (data2 > data3); + static const bool greater_than21 = (data2 > data1); + static const bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data1(values1); + static const Data data2(values2); + static const Data data3(values3); + + static const bool greater_than_equal12 = (data1 >= data2); + static const bool greater_than_equal23 = (data2 >= data3); + static const bool greater_than_equal21 = (data2 >= data1); + static const bool greater_than_equal32 = (data3 >= data2); + static const bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data1(values1); + static const DataTransparentComparator data2(values2); + static const DataTransparentComparator data3(values3); + + static const bool greater_than_equal12 = (data1 >= data2); + static const bool greater_than_equal23 = (data2 >= data3); + static const bool greater_than_equal21 = (data2 >= data1); + static const bool greater_than_equal32 = (data3 >= data2); + static const bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + }; +} diff --git a/test/test_const_multiset_ext_constexpr.cpp b/test/test_const_multiset_ext_constexpr.cpp new file mode 100644 index 00000000..da032198 --- /dev/null +++ b/test/test_const_multiset_ext_constexpr.cpp @@ -0,0 +1,1423 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2025 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the 'Software'), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "unit_test_framework.h" + +#include +#include +#include +#include + +#include "etl/const_multiset.h" +#include "etl/span.h" + +#include "data.h" + +namespace +{ + static constexpr size_t Max_Size = 10UL; + + //************************************************************************* + // The key type + //************************************************************************* + struct Key + { + // Default constructor + constexpr Key() + : k(0) + { + } + + // Construct from char key + constexpr explicit Key(char k_) + : k(k_) + { + } + + char k; + }; + + // Less-than operator for Key < Key + constexpr bool operator <(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k < rhs.k); + } + + // Less-than operator for Key < char + constexpr bool operator <(const Key& lhs, char rhs) noexcept + { + return (lhs.k < rhs); + } + + // Less-than operator for char < Key + constexpr bool operator <(char lhs, const Key& rhs) noexcept + { + return (lhs < rhs.k); + } + + // Equality operator for Key == Key + constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k == rhs.k); + } + + // Equality operator for Key != Key + constexpr bool operator !=(const Key& lhs, const Key& rhs) noexcept + { + return !(lhs.k == rhs.k); + } + +#define TEST_GREATER_THAN +#ifdef TEST_GREATER_THAN + using Data = etl::const_multiset_ext>; + using IData = etl::iconst_multiset>; + using DataTransparentComparator = etl::const_multiset_ext>; + using IDataTransparentComparator = etl::iconst_multiset>; +#else + using Data = etl::const_multiset_ext>; + using IData = etl::iconst_multiset>; + using DataTransparentComparator = etl::const_multiset_ext>; + using IDataTransparentComparator = etl::iconst_multiset>; +#endif + + using value_type = Data::value_type; + using key_type = Data::key_type; + using const_iterator = Data::const_iterator; + using span_type = etl::span; + + SUITE(test_const_multiset_ext_constexpr) + { + //************************************************************************* + TEST(test_default_constructor) + { + static constexpr Data data; + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 0UL); + CHECK_TRUE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == 0UL); + CHECK_TRUE(max_size == 0UL); + CHECK_TRUE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_min_size) + { + static constexpr value_type values[]{ Key('A') }; + + static constexpr Data data(values); + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 1U); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == 1U); + CHECK_TRUE(max_size == 1U); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr Data data(values); + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + +#if ETL_USING_CPP17 + //************************************************************************* + TEST(test_cpp17_deduced_constructor_from_span) + { + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr span_type span(values); + static constexpr etl::const_multiset_ext data{span}; + + etl::const_multiset check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } + + //************************************************************************* + TEST(test_cpp17_deduced_constructor_from_array) + { + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr etl::const_multiset_ext data{values}; + + etl::const_multiset check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } +#endif + + //************************************************************************* + TEST(test_begin_const) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr Data data(values); + + CHECK_TRUE(data.is_valid()); + static constexpr auto value = *data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(Key('J') == value); +#else + CHECK_TRUE(Key('A') == value); +#endif + } + + //************************************************************************* + TEST(test_end_const) + { + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; + + static constexpr Data data(values); + + static constexpr const_iterator end_itr = data.end(); + + CHECK_TRUE(end_itr == (data.begin() + data.size())); + } + + //************************************************************************* + TEST(test_equal_range_const) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr Data data(values); + + static constexpr ETL_OR_STD::pair resultA = data.equal_range(Key('A')); + static constexpr ETL_OR_STD::pair resultB = data.equal_range(Key('B')); + static constexpr ETL_OR_STD::pair resultC = data.equal_range(Key('C')); + static constexpr ETL_OR_STD::pair resultD = data.equal_range(Key('D')); + static constexpr ETL_OR_STD::pair resultE = data.equal_range(Key('E')); + static constexpr ETL_OR_STD::pair resultF = data.equal_range(Key('F')); + static constexpr ETL_OR_STD::pair resultG = data.equal_range(Key('G')); + static constexpr ETL_OR_STD::pair resultH = data.equal_range(Key('H')); + static constexpr ETL_OR_STD::pair resultI = data.equal_range(Key('I')); + static constexpr ETL_OR_STD::pair resultJ = data.equal_range(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_equal_range_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr DataTransparentComparator data(values); + + static constexpr ETL_OR_STD::pair resultA = data.equal_range('A'); + static constexpr ETL_OR_STD::pair resultB = data.equal_range('B'); + static constexpr ETL_OR_STD::pair resultC = data.equal_range('C'); + static constexpr ETL_OR_STD::pair resultD = data.equal_range('D'); + static constexpr ETL_OR_STD::pair resultE = data.equal_range('E'); + static constexpr ETL_OR_STD::pair resultF = data.equal_range('F'); + static constexpr ETL_OR_STD::pair resultG = data.equal_range('G'); + static constexpr ETL_OR_STD::pair resultH = data.equal_range('H'); + static constexpr ETL_OR_STD::pair resultI = data.equal_range('I'); + static constexpr ETL_OR_STD::pair resultJ = data.equal_range('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_const) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr Data data(values); + + static constexpr const_iterator resultA = data.lower_bound(Key('A')); + static constexpr const_iterator resultB = data.lower_bound(Key('B')); + static constexpr const_iterator resultC = data.lower_bound(Key('C')); + static constexpr const_iterator resultD = data.lower_bound(Key('D')); + static constexpr const_iterator resultE = data.lower_bound(Key('E')); + static constexpr const_iterator resultF = data.lower_bound(Key('F')); + static constexpr const_iterator resultG = data.lower_bound(Key('G')); + static constexpr const_iterator resultH = data.lower_bound(Key('H')); + static constexpr const_iterator resultI = data.lower_bound(Key('I')); + static constexpr const_iterator resultJ = data.lower_bound(Key('J')); + static constexpr const_iterator resultK = data.lower_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr DataTransparentComparator data(values); + + static constexpr const_iterator resultA = data.lower_bound('A'); + static constexpr const_iterator resultB = data.lower_bound('B'); + static constexpr const_iterator resultC = data.lower_bound('C'); + static constexpr const_iterator resultD = data.lower_bound('D'); + static constexpr const_iterator resultE = data.lower_bound('E'); + static constexpr const_iterator resultF = data.lower_bound('F'); + static constexpr const_iterator resultG = data.lower_bound('G'); + static constexpr const_iterator resultH = data.lower_bound('H'); + static constexpr const_iterator resultI = data.lower_bound('I'); + static constexpr const_iterator resultJ = data.lower_bound('J'); + static constexpr const_iterator resultK = data.lower_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_const) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr Data data(values); + + static constexpr const_iterator resultA = data.upper_bound(Key('A')); + static constexpr const_iterator resultB = data.upper_bound(Key('B')); + static constexpr const_iterator resultC = data.upper_bound(Key('C')); + static constexpr const_iterator resultD = data.upper_bound(Key('D')); + static constexpr const_iterator resultE = data.upper_bound(Key('E')); + static constexpr const_iterator resultF = data.upper_bound(Key('F')); + static constexpr const_iterator resultG = data.upper_bound(Key('G')); + static constexpr const_iterator resultH = data.upper_bound(Key('H')); + static constexpr const_iterator resultI = data.upper_bound(Key('I')); + static constexpr const_iterator resultJ = data.upper_bound(Key('J')); + static constexpr const_iterator resultK = data.upper_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr DataTransparentComparator data(values); + + static constexpr const_iterator resultA = data.upper_bound('A'); + static constexpr const_iterator resultB = data.upper_bound('B'); + static constexpr const_iterator resultC = data.upper_bound('C'); + static constexpr const_iterator resultD = data.upper_bound('D'); + static constexpr const_iterator resultE = data.upper_bound('E'); + static constexpr const_iterator resultF = data.upper_bound('F'); + static constexpr const_iterator resultG = data.upper_bound('G'); + static constexpr const_iterator resultH = data.upper_bound('H'); + static constexpr const_iterator resultI = data.upper_bound('I'); + static constexpr const_iterator resultJ = data.upper_bound('J'); + static constexpr const_iterator resultK = data.upper_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_count_const) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr Data data(values); + + CHECK_EQUAL(1, data.count(Key('A'))); + CHECK_EQUAL(1, data.count(Key('B'))); + CHECK_EQUAL(1, data.count(Key('C'))); + CHECK_EQUAL(1, data.count(Key('D'))); + CHECK_EQUAL(1, data.count(Key('E'))); + CHECK_EQUAL(1, data.count(Key('F'))); + CHECK_EQUAL(3, data.count(Key('G'))); + CHECK_EQUAL(0, data.count(Key('H'))); + CHECK_EQUAL(0, data.count(Key('I'))); + CHECK_EQUAL(1, data.count(Key('J'))); + CHECK_EQUAL(0, data.count(Key('K'))); + } + + //************************************************************************* + TEST(test_count_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr DataTransparentComparator data(values); + + CHECK_EQUAL(1, data.count('A')); + CHECK_EQUAL(1, data.count('B')); + CHECK_EQUAL(1, data.count('C')); + CHECK_EQUAL(1, data.count('D')); + CHECK_EQUAL(1, data.count('E')); + CHECK_EQUAL(1, data.count('F')); + CHECK_EQUAL(3, data.count('G')); + CHECK_EQUAL(0, data.count('H')); + CHECK_EQUAL(0, data.count('I')); + CHECK_EQUAL(1, data.count('J')); + CHECK_EQUAL(0, data.count('K')); + } + + //************************************************************************* + TEST(test_const_iterator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr Data data(values); + + const_iterator itr = data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE(itr == data.end()); +#else + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE(itr == data.end()); +#endif + } + + //************************************************************************* + TEST(test_find_const) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr Data data(values); + + static constexpr const_iterator resultA = data.find(Key('A')); + static constexpr const_iterator resultB = data.find(Key('B')); + static constexpr const_iterator resultC = data.find(Key('C')); + static constexpr const_iterator resultD = data.find(Key('D')); + static constexpr const_iterator resultE = data.find(Key('E')); + static constexpr const_iterator resultF = data.find(Key('F')); + static constexpr const_iterator resultG = data.find(Key('G')); + static constexpr const_iterator resultH = data.find(Key('H')); + static constexpr const_iterator resultI = data.find(Key('I')); + static constexpr const_iterator resultJ = data.find(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_find_const_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr DataTransparentComparator data(values); + + static constexpr const_iterator resultA = data.find('A'); + static constexpr const_iterator resultB = data.find('B'); + static constexpr const_iterator resultC = data.find('C'); + static constexpr const_iterator resultD = data.find('D'); + static constexpr const_iterator resultE = data.find('E'); + static constexpr const_iterator resultF = data.find('F'); + static constexpr const_iterator resultG = data.find('G'); + static constexpr const_iterator resultH = data.find('H'); + static constexpr const_iterator resultI = data.find('I'); + static constexpr const_iterator resultJ = data.find('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_contains_const) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr Data data(values); + + static constexpr bool containsA = data.contains(Key('A')); + static constexpr bool containsB = data.contains(Key('B')); + static constexpr bool containsC = data.contains(Key('C')); + static constexpr bool containsD = data.contains(Key('D')); + static constexpr bool containsE = data.contains(Key('E')); + static constexpr bool containsF = data.contains(Key('F')); + static constexpr bool containsG = data.contains(Key('G')); + static constexpr bool containsH = data.contains(Key('H')); + static constexpr bool containsI = data.contains(Key('I')); + static constexpr bool containsJ = data.contains(Key('J')); + static constexpr bool containsK = data.contains(Key('K')); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_FALSE(containsH); + CHECK_FALSE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_contains_with_transparent_comparator_const) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('G'), Key('G'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('G'), Key('J') }; +#endif + + static constexpr DataTransparentComparator data(values); + + static constexpr bool containsA = data.contains('A'); + static constexpr bool containsB = data.contains('B'); + static constexpr bool containsC = data.contains('C'); + static constexpr bool containsD = data.contains('D'); + static constexpr bool containsE = data.contains('E'); + static constexpr bool containsF = data.contains('F'); + static constexpr bool containsG = data.contains('G'); + static constexpr bool containsH = data.contains('H'); + static constexpr bool containsI = data.contains('I'); + static constexpr bool containsJ = data.contains('J'); + static constexpr bool containsK = data.contains('K'); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_FALSE(containsH); + CHECK_FALSE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_key_comp_const) + { + static constexpr Data data; + static constexpr Data::key_compare compare = data.key_comp(); + + static constexpr bool compareAA = compare(Key{ 'A' }, Key{ 'A' }); + static constexpr bool compareBA = compare(Key{ 'B' }, Key{ 'A' }); + static constexpr bool compareAB = compare(Key{ 'A' }, Key{ 'B' }); + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); + #else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); + #endif + } + + //************************************************************************* + TEST(test_key_comp_const_transparent_comparator) + { + static constexpr DataTransparentComparator data; + static constexpr DataTransparentComparator::key_compare compare = data.key_comp(); + + static constexpr bool compareAA = compare('A', 'A'); + static constexpr bool compareBA = compare('B', 'A'); + static constexpr bool compareAB = compare('A', 'B'); + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); + #else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); + #endif + } + + //************************************************************************* + TEST(test_value_comp_const) + { + static constexpr Data data; + static constexpr Data::value_compare compare = data.value_comp(); + + static constexpr bool compareAA1 = compare(Key('A'), Key('A')); + static constexpr bool compareAA2 = compare(Key('A'), Key{ 'A' }); + static constexpr bool compareAA3 = compare(Key{ 'A' }, Key('A')); + + static constexpr bool compareBA1 = compare(Key('B'), Key('A')); + static constexpr bool compareBA2 = compare(Key('B'), Key{ 'A' }); + static constexpr bool compareBA3 = compare(Key{ 'B' }, Key('A')); + + static constexpr bool compareAB1 = compare(Key('A'), Key('B')); + static constexpr bool compareAB2 = compare(Key('A'), Key{ 'B' }); + static constexpr bool compareAB3 = compare(Key{ 'A' }, Key('B'));; + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); + #else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); + #endif + } + + //************************************************************************* + TEST(test_value_comp_const_transparent_comparator) + { + static constexpr DataTransparentComparator data; + static constexpr DataTransparentComparator::value_compare compare = data.value_comp(); + + static constexpr bool compareAA1 = compare(Key('A'), Key('A')); + static constexpr bool compareAA2 = compare(Key('A'), 'A'); + static constexpr bool compareAA3 = compare('A', Key('A')); + + static constexpr bool compareBA1 = compare(Key('B'), Key('A')); + static constexpr bool compareBA2 = compare(Key('B'), 'A'); + static constexpr bool compareBA3 = compare('B', Key('A')); + + static constexpr bool compareAB1 = compare(Key('A'), Key('B')); + static constexpr bool compareAB2 = compare(Key('A'), 'B'); + static constexpr bool compareAB3 = compare('A', Key('B'));; + + #ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); + #else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); + #endif + } + + //************************************************************************* + TEST(test_equal) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static constexpr Data data1(values1); + static constexpr Data data2(values2); + static constexpr Data data3(values3); + static constexpr Data data4(values4); + + static constexpr bool equal12 = (data1 == data2); + static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_equal_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static constexpr DataTransparentComparator data1(values1); + static constexpr DataTransparentComparator data2(values2); + static constexpr DataTransparentComparator data3(values3); + static constexpr DataTransparentComparator data4(values4); + + static constexpr bool equal12 = (data1 == data2); + static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_not_equal) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static constexpr Data data1(values1); + static constexpr Data data2(values2); + static constexpr Data data3(values3); + static constexpr Data data4(values4); + + static constexpr bool not_equal12 = (data1 != data2); + static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_not_equal_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; + + static constexpr DataTransparentComparator data1(values1); + static constexpr DataTransparentComparator data2(values2); + static constexpr DataTransparentComparator data3(values3); + static constexpr DataTransparentComparator data4(values4); + + static constexpr bool not_equal12 = (data1 != data2); + static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_less_than) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data1(values1); + static constexpr Data data2(values2); + static constexpr Data data3(values3); + + static constexpr bool less_than12 = (data1 < data2); + static constexpr bool less_than23 = (data2 < data3); + static constexpr bool less_than21 = (data2 < data1); + static constexpr bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data1(values1); + static constexpr DataTransparentComparator data2(values2); + static constexpr DataTransparentComparator data3(values3); + + static constexpr bool less_than12 = (data1 < data2); + static constexpr bool less_than23 = (data2 < data3); + static constexpr bool less_than21 = (data2 < data1); + static constexpr bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data1(values1); + static constexpr Data data2(values2); + static constexpr Data data3(values3); + + static constexpr bool less_than_equal12 = (data1 <= data2); + static constexpr bool less_than_equal23 = (data2 <= data3); + static constexpr bool less_than_equal21 = (data2 <= data1); + static constexpr bool less_than_equal32 = (data3 <= data2); + static constexpr bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data1(values1); + static constexpr DataTransparentComparator data2(values2); + static constexpr DataTransparentComparator data3(values3); + + static constexpr bool less_than_equal12 = (data1 <= data2); + static constexpr bool less_than_equal23 = (data2 <= data3); + static constexpr bool less_than_equal21 = (data2 <= data1); + static constexpr bool less_than_equal32 = (data3 <= data2); + static constexpr bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data1(values1); + static constexpr Data data2(values2); + static constexpr Data data3(values3); + + static constexpr bool greater_than12 = (data1 > data2); + static constexpr bool greater_than23 = (data2 > data3); + static constexpr bool greater_than21 = (data2 > data1); + static constexpr bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data1(values1); + static constexpr DataTransparentComparator data2(values2); + static constexpr DataTransparentComparator data3(values3); + + static constexpr bool greater_than12 = (data1 > data2); + static constexpr bool greater_than23 = (data2 > data3); + static constexpr bool greater_than21 = (data2 > data1); + static constexpr bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data1(values1); + static constexpr Data data2(values2); + static constexpr Data data3(values3); + + static constexpr bool greater_than_equal12 = (data1 >= data2); + static constexpr bool greater_than_equal23 = (data2 >= data3); + static constexpr bool greater_than_equal21 = (data2 >= data1); + static constexpr bool greater_than_equal32 = (data3 >= data2); + static constexpr bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data1(values1); + static constexpr DataTransparentComparator data2(values2); + static constexpr DataTransparentComparator data3(values3); + + static constexpr bool greater_than_equal12 = (data1 >= data2); + static constexpr bool greater_than_equal23 = (data2 >= data3); + static constexpr bool greater_than_equal21 = (data2 >= data1); + static constexpr bool greater_than_equal32 = (data3 >= data2); + static constexpr bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + }; +} diff --git a/test/test_const_set.cpp b/test/test_const_set.cpp new file mode 100644 index 00000000..c923a3e2 --- /dev/null +++ b/test/test_const_set.cpp @@ -0,0 +1,1435 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2025 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the 'Software'), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "unit_test_framework.h" + +#include +#include +#include +#include + +#include "etl/const_set.h" + +namespace +{ + static const size_t Max_Size = 10UL; + + //************************************************************************* + // The key type + //************************************************************************* + struct Key + { + // Default constructor + constexpr Key() + : k(0) + { + } + + // Construct from char key + constexpr explicit Key(char k_) + : k(k_) + { + } + + char k; + }; + + // Less-than operator for Key < Key + constexpr bool operator <(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k < rhs.k); + } + + // Less-than operator for Key < char + constexpr bool operator <(const Key& lhs, char rhs) noexcept + { + return (lhs.k < rhs); + } + + // Less-than operator for char < Key + constexpr bool operator <(char lhs, const Key& rhs) noexcept + { + return (lhs < rhs.k); + } + + // Equality operator for Key == Key + constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k == rhs.k); + } + + // Equality operator for Key != Key + constexpr bool operator !=(const Key& lhs, const Key& rhs) noexcept + { + return !(lhs.k == rhs.k); + } + + #define TEST_GREATER_THAN + #ifdef TEST_GREATER_THAN + using Data = etl::const_set>; + using Data2 = etl::const_set>; + using IData = etl::iconst_set>; + using DataTransparentComparator = etl::const_set>; + using DataTransparentComparator2 = etl::const_set>; + using IDataTransparentComparator = etl::iconst_set>; + #else + using Data = etl::const_set>; + using Data2 = etl::const_set>; + using IData = etl::iconst_set>; + using DataTransparentComparator = etl::const_set>; + using DataTransparentComparator2 = etl::const_set>; + using IDataTransparentComparator = etl::iconst_set>; + #endif + + using value_type = Data::value_type; + using key_type = Data::key_type; + using const_iterator = Data::const_iterator; + + SUITE(test_const_set) + { + //************************************************************************* + TEST(test_default_constructor) + { + static const Data data; + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 0UL); + CHECK_TRUE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_TRUE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_min_size) + { + static const Data data{ Key('A') }; + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 1U); + CHECK_FALSE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size_status_from_iconst_set) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const IData& idata = data; + + static const bool is_valid = idata.is_valid(); + static const size_t size = idata.size(); + static const bool empty = idata.empty(); + static const bool full = idata.full(); + static const size_t capacity = idata.capacity(); + static const size_t max_size = idata.max_size(); + static const const_iterator begin = idata.begin(); + static const const_iterator end = idata.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + ////************************************************************************* + // Enable to check static_assert "Number of elements exceeds capacity" + ////************************************************************************* + //TEST(test_constructor_excess_size) + //{ + // static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + // Key('F'), 'G'), 'H'), Key('I'), Key('J'), + // Key('K'), 10 }; + //} + +#if ETL_USING_CPP17 + //************************************************************************* + TEST(test_cpp17_deduced_constructor) + { + static const etl::const_set data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + etl::const_set check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } +#endif + + //************************************************************************* + TEST(test_begin) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + CHECK_TRUE(data.is_valid()); + static const auto value = *data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(( Key('J')) == value); +#else + CHECK_TRUE(( Key('A')) == value); +#endif + } + + //************************************************************************* + TEST(test_end_const) + { + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const const_iterator end_itr = data.end(); + + CHECK_TRUE(end_itr == (data.begin() + data.size())); + } + + //************************************************************************* + TEST(test_equal_range) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const ETL_OR_STD::pair resultA = data.equal_range(Key('A')); + static const ETL_OR_STD::pair resultB = data.equal_range(Key('B')); + static const ETL_OR_STD::pair resultC = data.equal_range(Key('C')); + static const ETL_OR_STD::pair resultD = data.equal_range(Key('D')); + static const ETL_OR_STD::pair resultE = data.equal_range(Key('E')); + static const ETL_OR_STD::pair resultF = data.equal_range(Key('F')); + static const ETL_OR_STD::pair resultG = data.equal_range(Key('G')); + static const ETL_OR_STD::pair resultH = data.equal_range(Key('H')); + static const ETL_OR_STD::pair resultI = data.equal_range(Key('I')); + static const ETL_OR_STD::pair resultJ = data.equal_range(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_equal_range_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const ETL_OR_STD::pair resultA = data.equal_range('A'); + static const ETL_OR_STD::pair resultB = data.equal_range('B'); + static const ETL_OR_STD::pair resultC = data.equal_range('C'); + static const ETL_OR_STD::pair resultD = data.equal_range('D'); + static const ETL_OR_STD::pair resultE = data.equal_range('E'); + static const ETL_OR_STD::pair resultF = data.equal_range('F'); + static const ETL_OR_STD::pair resultG = data.equal_range('G'); + static const ETL_OR_STD::pair resultH = data.equal_range('H'); + static const ETL_OR_STD::pair resultI = data.equal_range('I'); + static const ETL_OR_STD::pair resultJ = data.equal_range('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static const const_iterator resultA = data.lower_bound(Key('A')); + static const const_iterator resultB = data.lower_bound(Key('B')); + static const const_iterator resultC = data.lower_bound(Key('C')); + static const const_iterator resultD = data.lower_bound(Key('D')); + static const const_iterator resultE = data.lower_bound(Key('E')); + static const const_iterator resultF = data.lower_bound(Key('F')); + static const const_iterator resultG = data.lower_bound(Key('G')); + static const const_iterator resultH = data.lower_bound(Key('H')); + static const const_iterator resultI = data.lower_bound(Key('I')); + static const const_iterator resultJ = data.lower_bound(Key('J')); + static const const_iterator resultK = data.lower_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static const const_iterator resultA = data.lower_bound('A'); + static const const_iterator resultB = data.lower_bound('B'); + static const const_iterator resultC = data.lower_bound('C'); + static const const_iterator resultD = data.lower_bound('D'); + static const const_iterator resultE = data.lower_bound('E'); + static const const_iterator resultF = data.lower_bound('F'); + static const const_iterator resultG = data.lower_bound('G'); + static const const_iterator resultH = data.lower_bound('H'); + static const const_iterator resultI = data.lower_bound('I'); + static const const_iterator resultJ = data.lower_bound('J'); + static const const_iterator resultK = data.lower_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static const const_iterator resultA = data.upper_bound(Key('A')); + static const const_iterator resultB = data.upper_bound(Key('B')); + static const const_iterator resultC = data.upper_bound(Key('C')); + static const const_iterator resultD = data.upper_bound(Key('D')); + static const const_iterator resultE = data.upper_bound(Key('E')); + static const const_iterator resultF = data.upper_bound(Key('F')); + static const const_iterator resultG = data.upper_bound(Key('G')); + static const const_iterator resultH = data.upper_bound(Key('H')); + static const const_iterator resultI = data.upper_bound(Key('I')); + static const const_iterator resultJ = data.upper_bound(Key('J')); + static const const_iterator resultK = data.upper_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static const const_iterator resultA = data.upper_bound('A'); + static const const_iterator resultB = data.upper_bound('B'); + static const const_iterator resultC = data.upper_bound('C'); + static const const_iterator resultD = data.upper_bound('D'); + static const const_iterator resultE = data.upper_bound('E'); + static const const_iterator resultF = data.upper_bound('F'); + static const const_iterator resultG = data.upper_bound('G'); + static const const_iterator resultH = data.upper_bound('H'); + static const const_iterator resultI = data.upper_bound('I'); + static const const_iterator resultJ = data.upper_bound('J'); + static const const_iterator resultK = data.upper_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_count) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const size_t countA = data.count(Key('A')); + static const size_t countB = data.count(Key('B')); + static const size_t countC = data.count(Key('C')); + static const size_t countD = data.count(Key('D')); + static const size_t countE = data.count(Key('E')); + static const size_t countF = data.count(Key('F')); + static const size_t countG = data.count(Key('G')); + static const size_t countH = data.count(Key('H')); + static const size_t countI = data.count(Key('I')); + static const size_t countJ = data.count(Key('J')); + static const size_t countK = data.count(Key('K')); + + CHECK_EQUAL(1, countA); + CHECK_EQUAL(1, countB); + CHECK_EQUAL(1, countC); + CHECK_EQUAL(1, countD); + CHECK_EQUAL(1, countE); + CHECK_EQUAL(1, countF); + CHECK_EQUAL(1, countG); + CHECK_EQUAL(1, countH); + CHECK_EQUAL(1, countI); + CHECK_EQUAL(1, countJ); + CHECK_EQUAL(0, countK); + } + + //************************************************************************* + TEST(test_count_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const size_t countA = data.count('A'); + static const size_t countB = data.count('B'); + static const size_t countC = data.count('C'); + static const size_t countD = data.count('D'); + static const size_t countE = data.count('E'); + static const size_t countF = data.count('F'); + static const size_t countG = data.count('G'); + static const size_t countH = data.count('H'); + static const size_t countI = data.count('I'); + static const size_t countJ = data.count('J'); + static const size_t countK = data.count('K'); + + CHECK_EQUAL(1, countA); + CHECK_EQUAL(1, countB); + CHECK_EQUAL(1, countC); + CHECK_EQUAL(1, countD); + CHECK_EQUAL(1, countE); + CHECK_EQUAL(1, countF); + CHECK_EQUAL(1, countG); + CHECK_EQUAL(1, countH); + CHECK_EQUAL(1, countI); + CHECK_EQUAL(1, countJ); + CHECK_EQUAL(0, countK); + } + + //************************************************************************* + TEST(test_const_iterator) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + const_iterator itr = data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE((Key('I')) == *itr++); + CHECK_TRUE((Key('H')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE(itr == data.end()); +#else + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('H')) == *itr++); + CHECK_TRUE((Key('I')) == *itr++); + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE(itr == data.end()); +#endif + } + + //************************************************************************* + TEST(test_find) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const const_iterator resultA = data.find(Key('A')); + static const const_iterator resultB = data.find(Key('B')); + static const const_iterator resultC = data.find(Key('C')); + static const const_iterator resultD = data.find(Key('D')); + static const const_iterator resultE = data.find(Key('E')); + static const const_iterator resultF = data.find(Key('F')); + static const const_iterator resultG = data.find(Key('G')); + static const const_iterator resultH = data.find(Key('H')); + static const const_iterator resultI = data.find(Key('I')); + static const const_iterator resultJ = data.find(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_find_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const const_iterator resultA = data.find('A'); + static const const_iterator resultB = data.find('B'); + static const const_iterator resultC = data.find('C'); + static const const_iterator resultD = data.find('D'); + static const const_iterator resultE = data.find('E'); + static const const_iterator resultF = data.find('F'); + static const const_iterator resultG = data.find('G'); + static const const_iterator resultH = data.find('H'); + static const const_iterator resultI = data.find('I'); + static const const_iterator resultJ = data.find('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_key_compare) + { + static const Data data; + + static const Data::key_compare compare = data.key_comp(); + + static const Data::key_type a(Key('A')); + static const Data::key_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_key_compare_using_transparent_comparator) + { + static const DataTransparentComparator data; + + static const DataTransparentComparator::key_compare compare = data.key_comp(); + + static const DataTransparentComparator::key_type a(Key('A')); + static const DataTransparentComparator::key_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_value_compare) + { + static const Data data; + + static const Data::value_compare compare = data.value_comp(); + + static const Data::value_type a(Key('A')); + static const Data::value_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_contains) + { +#ifdef TEST_GREATER_THAN + static const Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const bool containsA = data.contains(Key('A')); + static const bool containsB = data.contains(Key('B')); + static const bool containsC = data.contains(Key('C')); + static const bool containsD = data.contains(Key('D')); + static const bool containsE = data.contains(Key('E')); + static const bool containsF = data.contains(Key('F')); + static const bool containsG = data.contains(Key('G')); + static const bool containsH = data.contains(Key('H')); + static const bool containsI = data.contains(Key('I')); + static const bool containsJ = data.contains(Key('J')); + static const bool containsK = data.contains(Key('K')); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_TRUE(containsH); + CHECK_TRUE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_contains_with_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const DataTransparentComparator data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const bool containsA = data.contains('A'); + static const bool containsB = data.contains('B'); + static const bool containsC = data.contains('C'); + static const bool containsD = data.contains('D'); + static const bool containsE = data.contains('E'); + static const bool containsF = data.contains('F'); + static const bool containsG = data.contains('G'); + static const bool containsH = data.contains('H'); + static const bool containsI = data.contains('I'); + static const bool containsJ = data.contains('J'); + static const bool containsK = data.contains('K'); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_TRUE(containsH); + CHECK_TRUE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_key_comp) + { + static const Data data; + static const Data::key_compare compare = data.key_comp(); + + static const bool compareAA = compare(Key{ 'A' }, Key{ 'A' }); + static const bool compareBA = compare(Key{ 'B' }, Key{ 'A' }); + static const bool compareAB = compare(Key{ 'A' }, Key{ 'B' }); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); +#else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); +#endif + } + + //************************************************************************* + TEST(test_key_comp_transparent_comparator) + { + static const DataTransparentComparator data; + static const DataTransparentComparator::key_compare compare = data.key_comp(); + + static const bool compareAA = compare('A', 'A'); + static const bool compareBA = compare('B', 'A'); + static const bool compareAB = compare('A', 'B'); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); +#else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); +#endif + } + + //************************************************************************* + TEST(test_value_comp) + { + static const Data data; + static const Data::value_compare compare = data.value_comp(); + + static const bool compareAA1 = compare( Key{ 'A' }, Key{ 'A' }); + static const bool compareAA2 = compare( Key{ 'A' }, Key{ 'A' }); + static const bool compareAA3 = compare(Key{ 'A' }, Key{ 'A' }); + + static const bool compareBA1 = compare( Key{ 'B' }, Key{ 'A' }); + static const bool compareBA2 = compare( Key{ 'B' }, Key{ 'A' }); + static const bool compareBA3 = compare( Key{ 'B' }, Key{ 'A' }); + + static const bool compareAB1 = compare( Key{ 'A' }, Key{ 'B' }); + static const bool compareAB2 = compare( Key{ 'A' }, Key{ 'B' }); + static const bool compareAB3 = compare( Key{ 'A' }, Key{ 'B' });; + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); +#else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); +#endif + } + + //************************************************************************* + TEST(test_value_comp_transparent_comparator) + { + static const DataTransparentComparator data; + static const DataTransparentComparator::value_compare compare = data.value_comp(); + + static const bool compareAA1 = compare('A', 'A'); + static const bool compareAA2 = compare('A', 'A'); + static const bool compareAA3 = compare('A', 'A'); + + static const bool compareBA1 = compare('B', 'A'); + static const bool compareBA2 = compare('B', 'A'); + static const bool compareBA3 = compare('B', 'A'); + + static const bool compareAB1 = compare('A', 'B'); + static const bool compareAB2 = compare('A', 'B'); + static const bool compareAB3 = compare('A', 'B'); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); +#else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); +#endif + } + + //************************************************************************* + TEST(test_equal) + { + static const Data data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J') }; + + static const Data2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J'), Key('K') }; + + static const bool equal12 = (data1 == data2); + static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_equal_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J') }; + + static const DataTransparentComparator2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J'), Key('K') }; + + static const bool equal12 = (data1 == data2); + static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_not_equal) + { + static const Data data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J') }; + + static const Data2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J'), Key('K') }; + + static const bool not_equal12 = (data1 != data2); + static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_not_equal_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J') }; + + static const DataTransparentComparator2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J'), Key('K') }; + + static const bool not_equal12 = (data1 != data2); + static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_less_than) + { + static const Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J') }; + + static const bool less_than12 = (data1 < data2); + static const bool less_than23 = (data2 < data3); + static const bool less_than21 = (data2 < data1); + static const bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool less_than12 = (data1 < data2); + static const bool less_than23 = (data2 < data3); + static const bool less_than21 = (data2 < data1); + static const bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal) + { + static const Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool less_than_equal12 = (data1 <= data2); + static const bool less_than_equal23 = (data2 <= data3); + static const bool less_than_equal21 = (data2 <= data1); + static const bool less_than_equal32 = (data3 <= data2); + static const bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool less_than_equal12 = (data1 <= data2); + static const bool less_than_equal23 = (data2 <= data3); + static const bool less_than_equal21 = (data2 <= data1); + static const bool less_than_equal32 = (data3 <= data2); + static const bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than) + { + static const Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool greater_than12 = (data1 > data2); + static const bool greater_than23 = (data2 > data3); + static const bool greater_than21 = (data2 > data1); + static const bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool greater_than12 = (data1 > data2); + static const bool greater_than23 = (data2 > data3); + static const bool greater_than21 = (data2 > data1); + static const bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal) + { + static const Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool greater_than_equal12 = (data1 >= data2); + static const bool greater_than_equal23 = (data2 >= data3); + static const bool greater_than_equal21 = (data2 >= data1); + static const bool greater_than_equal32 = (data3 >= data2); + static const bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal_with_transparent_comparator) + { + static const DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const bool greater_than_equal12 = (data1 >= data2); + static const bool greater_than_equal23 = (data2 >= data3); + static const bool greater_than_equal21 = (data2 >= data1); + static const bool greater_than_equal32 = (data3 >= data2); + static const bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + }; +} diff --git a/test/test_const_set_constexpr.cpp b/test/test_const_set_constexpr.cpp new file mode 100644 index 00000000..0e2a0cfa --- /dev/null +++ b/test/test_const_set_constexpr.cpp @@ -0,0 +1,1434 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2025 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the 'Software'), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "unit_test_framework.h" + +#include +#include +#include +#include + +#include "etl/const_set.h" + +namespace +{ + static constexpr size_t Max_Size = 10UL; + + //************************************************************************* + // The key type + //************************************************************************* + struct Key + { + // Default constructor + constexpr Key() + : k(0) + { + } + + // Construct from char key + constexpr explicit Key(char k_) + : k(k_) + { + } + + char k; + }; + + // Less-than operator for Key < Key + constexpr bool operator <(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k < rhs.k); + } + + // Less-than operator for Key < char + constexpr bool operator <(const Key& lhs, char rhs) noexcept + { + return (lhs.k < rhs); + } + + // Less-than operator for char < Key + constexpr bool operator <(char lhs, const Key& rhs) noexcept + { + return (lhs < rhs.k); + } + + // Equality operator for Key == Key + constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k == rhs.k); + } + + // Equality operator for Key != Key + constexpr bool operator !=(const Key& lhs, const Key& rhs) noexcept + { + return !(lhs.k == rhs.k); + } + + #define TEST_GREATER_THAN + #ifdef TEST_GREATER_THAN + using Data = etl::const_set>; + using Data2 = etl::const_set>; + using IData = etl::iconst_set>; + using DataTransparentComparator = etl::const_set>; + using DataTransparentComparator2 = etl::const_set>; + using IDataTransparentComparator = etl::iconst_set>; + #else + using Data = etl::const_set>; + using Data2 = etl::const_set>; + using IData = etl::iconst_set>; + using DataTransparentComparator = etl::const_set>; + using DataTransparentComparator2 = etl::const_set>; + using IDataTransparentComparator = etl::iconst_set>; + #endif + + using value_type = Data::value_type; + using key_type = Data::key_type; + using const_iterator = Data::const_iterator; + + SUITE(test_const_set_constexpr) + { + //************************************************************************* + TEST(test_default_constructor) + { + static constexpr Data data; + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 0UL); + CHECK_TRUE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_TRUE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_min_size) + { + static constexpr Data data{ Key('A') }; + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 1U); + CHECK_FALSE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size_status_from_iconst_set) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr const IData& idata = data; + + static constexpr bool is_valid = idata.is_valid(); + static constexpr size_t size = idata.size(); + static constexpr bool empty = idata.empty(); + static constexpr bool full = idata.full(); + static constexpr size_t capacity = idata.capacity(); + static constexpr size_t max_size = idata.max_size(); + static constexpr const_iterator begin = idata.begin(); + static constexpr const_iterator end = idata.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + ////************************************************************************* + // Enable to check static_assert "Number of elements exceeds capacity" + ////************************************************************************* + //TEST(test_constructor_excess_size) + //{ + // static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + // Key('F'), 'G'), 'H'), Key('I'), Key('J'), + // Key('K'), 10 }; + //} + +#if ETL_USING_CPP17 + //************************************************************************* + TEST(test_cpp17_deduced_constructor) + { + static constexpr etl::const_set data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + etl::const_set check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } +#endif + + //************************************************************************* + TEST(test_begin) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + CHECK_TRUE(data.is_valid()); + static constexpr auto value = *data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(( Key('J')) == value); +#else + CHECK_TRUE(( Key('A')) == value); +#endif + } + + //************************************************************************* + TEST(test_end_const) + { + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr const_iterator end_itr = data.end(); + + CHECK_TRUE(end_itr == (data.begin() + data.size())); + } + + //************************************************************************* + TEST(test_equal_range) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr ETL_OR_STD::pair resultA = data.equal_range(Key('A')); + static constexpr ETL_OR_STD::pair resultB = data.equal_range(Key('B')); + static constexpr ETL_OR_STD::pair resultC = data.equal_range(Key('C')); + static constexpr ETL_OR_STD::pair resultD = data.equal_range(Key('D')); + static constexpr ETL_OR_STD::pair resultE = data.equal_range(Key('E')); + static constexpr ETL_OR_STD::pair resultF = data.equal_range(Key('F')); + static constexpr ETL_OR_STD::pair resultG = data.equal_range(Key('G')); + static constexpr ETL_OR_STD::pair resultH = data.equal_range(Key('H')); + static constexpr ETL_OR_STD::pair resultI = data.equal_range(Key('I')); + static constexpr ETL_OR_STD::pair resultJ = data.equal_range(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_equal_range_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr ETL_OR_STD::pair resultA = data.equal_range('A'); + static constexpr ETL_OR_STD::pair resultB = data.equal_range('B'); + static constexpr ETL_OR_STD::pair resultC = data.equal_range('C'); + static constexpr ETL_OR_STD::pair resultD = data.equal_range('D'); + static constexpr ETL_OR_STD::pair resultE = data.equal_range('E'); + static constexpr ETL_OR_STD::pair resultF = data.equal_range('F'); + static constexpr ETL_OR_STD::pair resultG = data.equal_range('G'); + static constexpr ETL_OR_STD::pair resultH = data.equal_range('H'); + static constexpr ETL_OR_STD::pair resultI = data.equal_range('I'); + static constexpr ETL_OR_STD::pair resultJ = data.equal_range('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static constexpr const_iterator resultA = data.lower_bound(Key('A')); + static constexpr const_iterator resultB = data.lower_bound(Key('B')); + static constexpr const_iterator resultC = data.lower_bound(Key('C')); + static constexpr const_iterator resultD = data.lower_bound(Key('D')); + static constexpr const_iterator resultE = data.lower_bound(Key('E')); + static constexpr const_iterator resultF = data.lower_bound(Key('F')); + static constexpr const_iterator resultG = data.lower_bound(Key('G')); + static constexpr const_iterator resultH = data.lower_bound(Key('H')); + static constexpr const_iterator resultI = data.lower_bound(Key('I')); + static constexpr const_iterator resultJ = data.lower_bound(Key('J')); + static constexpr const_iterator resultK = data.lower_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static constexpr const_iterator resultA = data.lower_bound('A'); + static constexpr const_iterator resultB = data.lower_bound('B'); + static constexpr const_iterator resultC = data.lower_bound('C'); + static constexpr const_iterator resultD = data.lower_bound('D'); + static constexpr const_iterator resultE = data.lower_bound('E'); + static constexpr const_iterator resultF = data.lower_bound('F'); + static constexpr const_iterator resultG = data.lower_bound('G'); + static constexpr const_iterator resultH = data.lower_bound('H'); + static constexpr const_iterator resultI = data.lower_bound('I'); + static constexpr const_iterator resultJ = data.lower_bound('J'); + static constexpr const_iterator resultK = data.lower_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static constexpr const_iterator resultA = data.upper_bound(Key('A')); + static constexpr const_iterator resultB = data.upper_bound(Key('B')); + static constexpr const_iterator resultC = data.upper_bound(Key('C')); + static constexpr const_iterator resultD = data.upper_bound(Key('D')); + static constexpr const_iterator resultE = data.upper_bound(Key('E')); + static constexpr const_iterator resultF = data.upper_bound(Key('F')); + static constexpr const_iterator resultG = data.upper_bound(Key('G')); + static constexpr const_iterator resultH = data.upper_bound(Key('H')); + static constexpr const_iterator resultI = data.upper_bound(Key('I')); + static constexpr const_iterator resultJ = data.upper_bound(Key('J')); + static constexpr const_iterator resultK = data.upper_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static constexpr const_iterator resultA = data.upper_bound('A'); + static constexpr const_iterator resultB = data.upper_bound('B'); + static constexpr const_iterator resultC = data.upper_bound('C'); + static constexpr const_iterator resultD = data.upper_bound('D'); + static constexpr const_iterator resultE = data.upper_bound('E'); + static constexpr const_iterator resultF = data.upper_bound('F'); + static constexpr const_iterator resultG = data.upper_bound('G'); + static constexpr const_iterator resultH = data.upper_bound('H'); + static constexpr const_iterator resultI = data.upper_bound('I'); + static constexpr const_iterator resultJ = data.upper_bound('J'); + static constexpr const_iterator resultK = data.upper_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_count) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr size_t countA = data.count(Key('A')); + static constexpr size_t countB = data.count(Key('B')); + static constexpr size_t countC = data.count(Key('C')); + static constexpr size_t countD = data.count(Key('D')); + static constexpr size_t countE = data.count(Key('E')); + static constexpr size_t countF = data.count(Key('F')); + static constexpr size_t countG = data.count(Key('G')); + static constexpr size_t countH = data.count(Key('H')); + static constexpr size_t countI = data.count(Key('I')); + static constexpr size_t countJ = data.count(Key('J')); + static constexpr size_t countK = data.count(Key('K')); + + CHECK_EQUAL(1, countA); + CHECK_EQUAL(1, countB); + CHECK_EQUAL(1, countC); + CHECK_EQUAL(1, countD); + CHECK_EQUAL(1, countE); + CHECK_EQUAL(1, countF); + CHECK_EQUAL(1, countG); + CHECK_EQUAL(1, countH); + CHECK_EQUAL(1, countI); + CHECK_EQUAL(1, countJ); + CHECK_EQUAL(0, countK); + } + + //************************************************************************* + TEST(test_count_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr size_t countA = data.count('A'); + static constexpr size_t countB = data.count('B'); + static constexpr size_t countC = data.count('C'); + static constexpr size_t countD = data.count('D'); + static constexpr size_t countE = data.count('E'); + static constexpr size_t countF = data.count('F'); + static constexpr size_t countG = data.count('G'); + static constexpr size_t countH = data.count('H'); + static constexpr size_t countI = data.count('I'); + static constexpr size_t countJ = data.count('J'); + static constexpr size_t countK = data.count('K'); + + CHECK_EQUAL(1, countA); + CHECK_EQUAL(1, countB); + CHECK_EQUAL(1, countC); + CHECK_EQUAL(1, countD); + CHECK_EQUAL(1, countE); + CHECK_EQUAL(1, countF); + CHECK_EQUAL(1, countG); + CHECK_EQUAL(1, countH); + CHECK_EQUAL(1, countI); + CHECK_EQUAL(1, countJ); + CHECK_EQUAL(0, countK); + } + + //************************************************************************* + TEST(test_const_iterator) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + const_iterator itr = data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE((Key('I')) == *itr++); + CHECK_TRUE((Key('H')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE(itr == data.end()); +#else + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('H')) == *itr++); + CHECK_TRUE((Key('I')) == *itr++); + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE(itr == data.end()); +#endif + } + + //************************************************************************* + TEST(test_find) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr const_iterator resultA = data.find(Key('A')); + static constexpr const_iterator resultB = data.find(Key('B')); + static constexpr const_iterator resultC = data.find(Key('C')); + static constexpr const_iterator resultD = data.find(Key('D')); + static constexpr const_iterator resultE = data.find(Key('E')); + static constexpr const_iterator resultF = data.find(Key('F')); + static constexpr const_iterator resultG = data.find(Key('G')); + static constexpr const_iterator resultH = data.find(Key('H')); + static constexpr const_iterator resultI = data.find(Key('I')); + static constexpr const_iterator resultJ = data.find(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_find_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr const_iterator resultA = data.find('A'); + static constexpr const_iterator resultB = data.find('B'); + static constexpr const_iterator resultC = data.find('C'); + static constexpr const_iterator resultD = data.find('D'); + static constexpr const_iterator resultE = data.find('E'); + static constexpr const_iterator resultF = data.find('F'); + static constexpr const_iterator resultG = data.find('G'); + static constexpr const_iterator resultH = data.find('H'); + static constexpr const_iterator resultI = data.find('I'); + static constexpr const_iterator resultJ = data.find('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_key_compare) + { + static constexpr Data data; + + static constexpr Data::key_compare compare = data.key_comp(); + + static constexpr Data::key_type a(Key('A')); + static constexpr Data::key_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_key_compare_using_transparent_comparator) + { + static constexpr DataTransparentComparator data; + + static constexpr DataTransparentComparator::key_compare compare = data.key_comp(); + + static constexpr DataTransparentComparator::key_type a(Key('A')); + static constexpr DataTransparentComparator::key_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_value_compare) + { + static constexpr Data data; + + static constexpr Data::value_compare compare = data.value_comp(); + + static constexpr Data::value_type a(Key('A')); + static constexpr Data::value_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_contains) + { +#ifdef TEST_GREATER_THAN + static constexpr Data data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr Data data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr bool containsA = data.contains(Key('A')); + static constexpr bool containsB = data.contains(Key('B')); + static constexpr bool containsC = data.contains(Key('C')); + static constexpr bool containsD = data.contains(Key('D')); + static constexpr bool containsE = data.contains(Key('E')); + static constexpr bool containsF = data.contains(Key('F')); + static constexpr bool containsG = data.contains(Key('G')); + static constexpr bool containsH = data.contains(Key('H')); + static constexpr bool containsI = data.contains(Key('I')); + static constexpr bool containsJ = data.contains(Key('J')); + static constexpr bool containsK = data.contains(Key('K')); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_TRUE(containsH); + CHECK_TRUE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_contains_with_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr DataTransparentComparator data{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr DataTransparentComparator data{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr bool containsA = data.contains('A'); + static constexpr bool containsB = data.contains('B'); + static constexpr bool containsC = data.contains('C'); + static constexpr bool containsD = data.contains('D'); + static constexpr bool containsE = data.contains('E'); + static constexpr bool containsF = data.contains('F'); + static constexpr bool containsG = data.contains('G'); + static constexpr bool containsH = data.contains('H'); + static constexpr bool containsI = data.contains('I'); + static constexpr bool containsJ = data.contains('J'); + static constexpr bool containsK = data.contains('K'); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_TRUE(containsH); + CHECK_TRUE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_key_comp) + { + static constexpr Data data; + static constexpr Data::key_compare compare = data.key_comp(); + + static constexpr bool compareAA = compare(Key{ 'A' }, Key{ 'A' }); + static constexpr bool compareBA = compare(Key{ 'B' }, Key{ 'A' }); + static constexpr bool compareAB = compare(Key{ 'A' }, Key{ 'B' }); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); +#else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); +#endif + } + + //************************************************************************* + TEST(test_key_comp_transparent_comparator) + { + static constexpr DataTransparentComparator data; + static constexpr DataTransparentComparator::key_compare compare = data.key_comp(); + + static constexpr bool compareAA = compare('A', 'A'); + static constexpr bool compareBA = compare('B', 'A'); + static constexpr bool compareAB = compare('A', 'B'); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); +#else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); +#endif + } + + //************************************************************************* + TEST(test_value_comp) + { + static constexpr Data data; + static constexpr Data::value_compare compare = data.value_comp(); + + static constexpr bool compareAA1 = compare( Key{ 'A' }, Key{ 'A' }); + static constexpr bool compareAA2 = compare( Key{ 'A' }, Key{ 'A' }); + static constexpr bool compareAA3 = compare(Key{ 'A' }, Key{ 'A' }); + + static constexpr bool compareBA1 = compare( Key{ 'B' }, Key{ 'A' }); + static constexpr bool compareBA2 = compare( Key{ 'B' }, Key{ 'A' }); + static constexpr bool compareBA3 = compare( Key{ 'B' }, Key{ 'A' }); + + static constexpr bool compareAB1 = compare( Key{ 'A' }, Key{ 'B' }); + static constexpr bool compareAB2 = compare( Key{ 'A' }, Key{ 'B' }); + static constexpr bool compareAB3 = compare( Key{ 'A' }, Key{ 'B' });; + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); +#else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); +#endif + } + + //************************************************************************* + TEST(test_value_comp_transparent_comparator) + { + static constexpr DataTransparentComparator data; + static constexpr DataTransparentComparator::value_compare compare = data.value_comp(); + + static constexpr bool compareAA1 = compare('A', 'A'); + static constexpr bool compareAA2 = compare('A', 'A'); + static constexpr bool compareAA3 = compare('A', 'A'); + + static constexpr bool compareBA1 = compare('B', 'A'); + static constexpr bool compareBA2 = compare('B', 'A'); + static constexpr bool compareBA3 = compare('B', 'A'); + + static constexpr bool compareAB1 = compare('A', 'B'); + static constexpr bool compareAB2 = compare('A', 'B'); + static constexpr bool compareAB3 = compare('A', 'B'); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); +#else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); +#endif + } + + //************************************************************************* + TEST(test_equal) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J') }; + + static constexpr Data2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J'), Key('K') }; + + static constexpr bool equal12 = etl::equal(data1.begin(), data1.end(), data2.begin()); + static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_equal_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J'), Key('K') }; + + static constexpr bool equal12 = (data1 == data2); + static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + } + + //************************************************************************* + TEST(test_not_equal) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J') }; + + static constexpr Data2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J'), Key('K') }; + + static constexpr bool not_equal12 = (data1 != data2); + static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_not_equal_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator2 data4{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J'), Key('K') }; + + static constexpr bool not_equal12 = (data1 != data2); + static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_less_than) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('K'), Key('I'), Key('J') }; + + static constexpr bool less_than12 = (data1 < data2); + static constexpr bool less_than23 = (data2 < data3); + static constexpr bool less_than21 = (data2 < data1); + static constexpr bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool less_than12 = (data1 < data2); + static constexpr bool less_than23 = (data2 < data3); + static constexpr bool less_than21 = (data2 < data1); + static constexpr bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool less_than_equal12 = (data1 <= data2); + static constexpr bool less_than_equal23 = (data2 <= data3); + static constexpr bool less_than_equal21 = (data2 <= data1); + static constexpr bool less_than_equal32 = (data3 <= data2); + static constexpr bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool less_than_equal12 = (data1 <= data2); + static constexpr bool less_than_equal23 = (data2 <= data3); + static constexpr bool less_than_equal21 = (data2 <= data1); + static constexpr bool less_than_equal32 = (data3 <= data2); + static constexpr bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool greater_than12 = (data1 > data2); + static constexpr bool greater_than23 = (data2 > data3); + static constexpr bool greater_than21 = (data2 > data1); + static constexpr bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool greater_than12 = (data1 > data2); + static constexpr bool greater_than23 = (data2 > data3); + static constexpr bool greater_than21 = (data2 > data1); + static constexpr bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal) + { + static constexpr Data data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool greater_than_equal12 = (data1 >= data2); + static constexpr bool greater_than_equal23 = (data2 >= data3); + static constexpr bool greater_than_equal21 = (data2 >= data1); + static constexpr bool greater_than_equal32 = (data3 >= data2); + static constexpr bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal_with_transparent_comparator) + { + static constexpr DataTransparentComparator data1{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data2{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data3{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr bool greater_than_equal12 = (data1 >= data2); + static constexpr bool greater_than_equal23 = (data2 >= data3); + static constexpr bool greater_than_equal21 = (data2 >= data1); + static constexpr bool greater_than_equal32 = (data3 >= data2); + static constexpr bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + }; +} diff --git a/test/test_const_set_ext.cpp b/test/test_const_set_ext.cpp new file mode 100644 index 00000000..b96fffb4 --- /dev/null +++ b/test/test_const_set_ext.cpp @@ -0,0 +1,1570 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2025 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the 'Software'), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "unit_test_framework.h" + +#include +#include +#include +#include +#include +#include +#include + +#include "etl/const_set.h" +#include "etl/span.h" + +#include "data.h" + +namespace +{ + static const size_t Max_Size = 10UL; + + //************************************************************************* + // The key type + //************************************************************************* + struct Key + { + // Default constructor + constexpr Key() + : k(0) + { + } + + // Construct from char key + constexpr explicit Key(char k_) + : k(k_) + { + } + + char k; + }; + + // Less-than operator for Key < Key + constexpr bool operator <(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k < rhs.k); + } + + // Less-than operator for Key < char + constexpr bool operator <(const Key& lhs, char rhs) noexcept + { + return (lhs.k < rhs); + } + + // Less-than operator for char < Key + constexpr bool operator <(char lhs, const Key& rhs) noexcept + { + return (lhs < rhs.k); + } + + // Equality operator for Key == Key + constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k == rhs.k); + } + + // Equality operator for Key != Key + constexpr bool operator !=(const Key& lhs, const Key& rhs) noexcept + { + return !(lhs.k == rhs.k); + } + + #define TEST_GREATER_THAN + #ifdef TEST_GREATER_THAN + using Data = etl::const_set_ext>; + using IData = etl::iconst_set>; + using DataTransparentComparator = etl::const_set_ext>; + using IDataTransparentComparator = etl::iconst_set>; + #else + using Data = etl::const_set_ext>; + using IData = etl::iconst_set>; + using DataTransparentComparator = etl::const_set_ext>; + using IDataTransparentComparator = etl::iconst_set>; + #endif + + using value_type = Data::value_type; + using key_type = Data::key_type; + using const_iterator = Data::const_iterator; + using span_type = etl::span; + + SUITE(test_const_set_ext) + { + //************************************************************************* + TEST(test_default_constructor) + { + static const Data data; + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 0UL); + CHECK_TRUE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == 0); + CHECK_TRUE(max_size == 0); + CHECK_TRUE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_min_size_from_span) + { + static const value_type values[]{ Key('A') }; + static const etl::span span(values); + static const Data data{ span }; + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 1U); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == span.size()); + CHECK_TRUE(max_size == span.size()); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size_from_span) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const span_type span(values); + static const Data data{ span }; + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size_from_array) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const Data data{ values }; + + static const bool is_valid = data.is_valid(); + static const size_t size = data.size(); + static const bool empty = data.empty(); + static const bool full = data.full(); + static const size_t capacity = data.capacity(); + static const size_t max_size = data.max_size(); + static const const_iterator begin = data.begin(); + static const const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size_status_from_iconst_set) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const Data data{ values }; + + static const IData& idata = data; + + static const bool is_valid = idata.is_valid(); + static const size_t size = idata.size(); + static const bool empty = idata.empty(); + static const bool full = idata.full(); + static const size_t capacity = idata.capacity(); + static const size_t max_size = idata.max_size(); + static const const_iterator begin = idata.begin(); + static const const_iterator end = idata.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + +#if ETL_USING_CPP17 + //************************************************************************* + TEST(test_cpp17_deduced_constructor_from_span) + { + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const span_type span(values); + static const etl::const_set_ext data{span}; + + etl::const_set check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } + + //************************************************************************* + TEST(test_cpp17_deduced_constructor_from_array) + { + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const etl::const_set_ext data{values}; + + etl::const_set check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } +#endif + + //************************************************************************* + TEST(test_begin) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const Data data{ values }; + + CHECK_TRUE(data.is_valid()); + static const auto value = *data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(( Key('J')) == value); +#else + CHECK_TRUE(( Key('A')) == value); +#endif + } + + //************************************************************************* + TEST(test_end) + { + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; + + static const Data data{ values }; + + static const const_iterator end_itr = data.end(); + + CHECK_TRUE(end_itr == (data.begin() + data.size())); + } + + //************************************************************************* + TEST(test_equal_range) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const Data data{ values }; + + static const ETL_OR_STD::pair resultA = data.equal_range(Key('A')); + static const ETL_OR_STD::pair resultB = data.equal_range(Key('B')); + static const ETL_OR_STD::pair resultC = data.equal_range(Key('C')); + static const ETL_OR_STD::pair resultD = data.equal_range(Key('D')); + static const ETL_OR_STD::pair resultE = data.equal_range(Key('E')); + static const ETL_OR_STD::pair resultF = data.equal_range(Key('F')); + static const ETL_OR_STD::pair resultG = data.equal_range(Key('G')); + static const ETL_OR_STD::pair resultH = data.equal_range(Key('H')); + static const ETL_OR_STD::pair resultI = data.equal_range(Key('I')); + static const ETL_OR_STD::pair resultJ = data.equal_range(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_equal_range_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const DataTransparentComparator data{ values }; + + static const ETL_OR_STD::pair resultA = data.equal_range('A'); + static const ETL_OR_STD::pair resultB = data.equal_range('B'); + static const ETL_OR_STD::pair resultC = data.equal_range('C'); + static const ETL_OR_STD::pair resultD = data.equal_range('D'); + static const ETL_OR_STD::pair resultE = data.equal_range('E'); + static const ETL_OR_STD::pair resultF = data.equal_range('F'); + static const ETL_OR_STD::pair resultG = data.equal_range('G'); + static const ETL_OR_STD::pair resultH = data.equal_range('H'); + static const ETL_OR_STD::pair resultI = data.equal_range('I'); + static const ETL_OR_STD::pair resultJ = data.equal_range('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static const Data data{ values }; + + static const const_iterator resultA = data.lower_bound(Key('A')); + static const const_iterator resultB = data.lower_bound(Key('B')); + static const const_iterator resultC = data.lower_bound(Key('C')); + static const const_iterator resultD = data.lower_bound(Key('D')); + static const const_iterator resultE = data.lower_bound(Key('E')); + static const const_iterator resultF = data.lower_bound(Key('F')); + static const const_iterator resultG = data.lower_bound(Key('G')); + static const const_iterator resultH = data.lower_bound(Key('H')); + static const const_iterator resultI = data.lower_bound(Key('I')); + static const const_iterator resultJ = data.lower_bound(Key('J')); + static const const_iterator resultK = data.lower_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static const DataTransparentComparator data{ values }; + + static const const_iterator resultA = data.lower_bound('A'); + static const const_iterator resultB = data.lower_bound('B'); + static const const_iterator resultC = data.lower_bound('C'); + static const const_iterator resultD = data.lower_bound('D'); + static const const_iterator resultE = data.lower_bound('E'); + static const const_iterator resultF = data.lower_bound('F'); + static const const_iterator resultG = data.lower_bound('G'); + static const const_iterator resultH = data.lower_bound('H'); + static const const_iterator resultI = data.lower_bound('I'); + static const const_iterator resultJ = data.lower_bound('J'); + static const const_iterator resultK = data.lower_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static const Data data{ values }; + + static const const_iterator resultA = data.upper_bound(Key('A')); + static const const_iterator resultB = data.upper_bound(Key('B')); + static const const_iterator resultC = data.upper_bound(Key('C')); + static const const_iterator resultD = data.upper_bound(Key('D')); + static const const_iterator resultE = data.upper_bound(Key('E')); + static const const_iterator resultF = data.upper_bound(Key('F')); + static const const_iterator resultG = data.upper_bound(Key('G')); + static const const_iterator resultH = data.upper_bound(Key('H')); + static const const_iterator resultI = data.upper_bound(Key('I')); + static const const_iterator resultJ = data.upper_bound(Key('J')); + static const const_iterator resultK = data.upper_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static const DataTransparentComparator data{ values }; + + static const const_iterator resultA = data.upper_bound('A'); + static const const_iterator resultB = data.upper_bound('B'); + static const const_iterator resultC = data.upper_bound('C'); + static const const_iterator resultD = data.upper_bound('D'); + static const const_iterator resultE = data.upper_bound('E'); + static const const_iterator resultF = data.upper_bound('F'); + static const const_iterator resultG = data.upper_bound('G'); + static const const_iterator resultH = data.upper_bound('H'); + static const const_iterator resultI = data.upper_bound('I'); + static const const_iterator resultJ = data.upper_bound('J'); + static const const_iterator resultK = data.upper_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_count) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const Data data{ values }; + + static const size_t countA = data.count(Key('A')); + static const size_t countB = data.count(Key('B')); + static const size_t countC = data.count(Key('C')); + static const size_t countD = data.count(Key('D')); + static const size_t countE = data.count(Key('E')); + static const size_t countF = data.count(Key('F')); + static const size_t countG = data.count(Key('G')); + static const size_t countH = data.count(Key('H')); + static const size_t countI = data.count(Key('I')); + static const size_t countJ = data.count(Key('J')); + static const size_t countK = data.count(Key('K')); + + CHECK_EQUAL(1, countA); + CHECK_EQUAL(1, countB); + CHECK_EQUAL(1, countC); + CHECK_EQUAL(1, countD); + CHECK_EQUAL(1, countE); + CHECK_EQUAL(1, countF); + CHECK_EQUAL(1, countG); + CHECK_EQUAL(1, countH); + CHECK_EQUAL(1, countI); + CHECK_EQUAL(1, countJ); + CHECK_EQUAL(0, countK); + } + + //************************************************************************* + TEST(test_count_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const DataTransparentComparator data{ values }; + + static const size_t countA = data.count('A'); + static const size_t countB = data.count('B'); + static const size_t countC = data.count('C'); + static const size_t countD = data.count('D'); + static const size_t countE = data.count('E'); + static const size_t countF = data.count('F'); + static const size_t countG = data.count('G'); + static const size_t countH = data.count('H'); + static const size_t countI = data.count('I'); + static const size_t countJ = data.count('J'); + static const size_t countK = data.count('K'); + + CHECK_EQUAL(1, countA); + CHECK_EQUAL(1, countB); + CHECK_EQUAL(1, countC); + CHECK_EQUAL(1, countD); + CHECK_EQUAL(1, countE); + CHECK_EQUAL(1, countF); + CHECK_EQUAL(1, countG); + CHECK_EQUAL(1, countH); + CHECK_EQUAL(1, countI); + CHECK_EQUAL(1, countJ); + CHECK_EQUAL(0, countK); + } + + //************************************************************************* + TEST(test_const_iterator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const Data data{ values }; + + const_iterator itr = data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE((Key('I')) == *itr++); + CHECK_TRUE((Key('H')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE(itr == data.end()); +#else + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('H')) == *itr++); + CHECK_TRUE((Key('I')) == *itr++); + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE(itr == data.end()); +#endif + } + + //************************************************************************* + TEST(test_find) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const Data data{ values }; + + static const const_iterator resultA = data.find(Key('A')); + static const const_iterator resultB = data.find(Key('B')); + static const const_iterator resultC = data.find(Key('C')); + static const const_iterator resultD = data.find(Key('D')); + static const const_iterator resultE = data.find(Key('E')); + static const const_iterator resultF = data.find(Key('F')); + static const const_iterator resultG = data.find(Key('G')); + static const const_iterator resultH = data.find(Key('H')); + static const const_iterator resultI = data.find(Key('I')); + static const const_iterator resultJ = data.find(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_find_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const DataTransparentComparator data{ values }; + + static const const_iterator resultA = data.find('A'); + static const const_iterator resultB = data.find('B'); + static const const_iterator resultC = data.find('C'); + static const const_iterator resultD = data.find('D'); + static const const_iterator resultE = data.find('E'); + static const const_iterator resultF = data.find('F'); + static const const_iterator resultG = data.find('G'); + static const const_iterator resultH = data.find('H'); + static const const_iterator resultI = data.find('I'); + static const const_iterator resultJ = data.find('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_key_compare) + { + static const Data data; + + static const Data::key_compare compare = data.key_comp(); + + static const Data::key_type a(Key('A')); + static const Data::key_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_key_compare_using_transparent_comparator) + { + static const DataTransparentComparator data; + static const DataTransparentComparator::key_compare compare = data.key_comp(); + + static const DataTransparentComparator::key_type a(Key('A')); + static const DataTransparentComparator::key_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_value_compare) + { + static const Data data; + static const Data::value_compare compare = data.value_comp(); + + static const Data::value_type a(Key('A')); + static const Data::value_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_contains) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const Data data{ values }; + + static const bool containsA = data.contains(Key('A')); + static const bool containsB = data.contains(Key('B')); + static const bool containsC = data.contains(Key('C')); + static const bool containsD = data.contains(Key('D')); + static const bool containsE = data.contains(Key('E')); + static const bool containsF = data.contains(Key('F')); + static const bool containsG = data.contains(Key('G')); + static const bool containsH = data.contains(Key('H')); + static const bool containsI = data.contains(Key('I')); + static const bool containsJ = data.contains(Key('J')); + static const bool containsK = data.contains(Key('K')); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_TRUE(containsH); + CHECK_TRUE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_contains_with_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static const value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static const value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static const DataTransparentComparator data{ values }; + + static const bool containsA = data.contains('A'); + static const bool containsB = data.contains('B'); + static const bool containsC = data.contains('C'); + static const bool containsD = data.contains('D'); + static const bool containsE = data.contains('E'); + static const bool containsF = data.contains('F'); + static const bool containsG = data.contains('G'); + static const bool containsH = data.contains('H'); + static const bool containsI = data.contains('I'); + static const bool containsJ = data.contains('J'); + static const bool containsK = data.contains('K'); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_TRUE(containsH); + CHECK_TRUE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_key_comp) + { + static const Data data; + static const Data::key_compare compare = data.key_comp(); + + static const bool compareAA = compare(Key{ 'A' }, Key{ 'A' }); + static const bool compareBA = compare(Key{ 'B' }, Key{ 'A' }); + static const bool compareAB = compare(Key{ 'A' }, Key{ 'B' }); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); +#else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); +#endif + } + + //************************************************************************* + TEST(test_key_comp_transparent_comparator) + { + static const DataTransparentComparator data; + static const DataTransparentComparator::key_compare compare = data.key_comp(); + + static const bool compareAA = compare('A', 'A'); + static const bool compareBA = compare('B', 'A'); + static const bool compareAB = compare('A', 'B'); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); +#else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); +#endif + } + + //************************************************************************* + TEST(test_value_comp) + { + static const Data data; + static const Data::value_compare compare = data.value_comp(); + + static const bool compareAA1 = compare( Key{ 'A' }, Key{ 'A' }); + static const bool compareAA2 = compare( Key{ 'A' }, Key{ 'A' }); + static const bool compareAA3 = compare(Key{ 'A' }, Key{ 'A' }); + + static const bool compareBA1 = compare( Key{ 'B' }, Key{ 'A' }); + static const bool compareBA2 = compare( Key{ 'B' }, Key{ 'A' }); + static const bool compareBA3 = compare(Key{ 'B' }, Key{ 'A' }); + + static const bool compareAB1 = compare( Key{ 'A' }, Key{ 'B' }); + static const bool compareAB2 = compare( Key{ 'A' }, Key{ 'B' }); + static const bool compareAB3 = compare(Key{ 'A' }, Key{ 'B' });; + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); +#else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); +#endif + } + + //************************************************************************* + TEST(test_value_comp_transparent_comparator) + { + static const DataTransparentComparator data; + static const DataTransparentComparator::value_compare compare = data.value_comp(); + + static const bool compareAA1 = compare( 'A', 'A'); + static const bool compareAA2 = compare( 'A', 'A'); + static const bool compareAA3 = compare('A', 'A'); + + static const bool compareBA1 = compare( 'B', 'A'); + static const bool compareBA2 = compare( 'B', 'A'); + static const bool compareBA3 = compare('B', 'A'); + + static const bool compareAB1 = compare( 'A', 'B'); + static const bool compareAB2 = compare( 'A', 'B'); + static const bool compareAB3 = compare('A', 'B');; + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); +#else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); +#endif + } + + //************************************************************************* + TEST(test_equal) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J'), Key('K') }; + + static const Data data1{values1}; + static const Data data2{values2}; + static const Data data3{values3}; + static const Data data4{values4}; + + static const bool equal12 = (data1 == data2); + static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_equal_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J'), Key('K') }; + + static const DataTransparentComparator data1{values1}; + static const DataTransparentComparator data2{values2}; + static const DataTransparentComparator data3{values3}; + static const DataTransparentComparator data4{values4}; + + static const bool equal12 = (data1 == data2); + static const bool equal13 = (data1 == data3); + static const bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_not_equal) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J'), Key('K') }; + + static const Data data1{values1}; + static const Data data2{values2}; + static const Data data3{values3}; + static const Data data4{values4}; + + static const bool not_equal12 = (data1 != data2); + static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_not_equal_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static const value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J'), Key('K') }; + + static const DataTransparentComparator data1{values1}; + static const DataTransparentComparator data2{values2}; + static const DataTransparentComparator data3{values3}; + static const DataTransparentComparator data4{values4}; + + static const bool not_equal12 = (data1 != data2); + static const bool not_equal13 = (data1 != data3); + static const bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_less_than) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data1{values1}; + static const Data data2{values2}; + static const Data data3{values3}; + + static const bool less_than12 = (data1 < data2); + static const bool less_than23 = (data2 < data3); + static const bool less_than21 = (data2 < data1); + static const bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data1{values1}; + static const DataTransparentComparator data2{values2}; + static const DataTransparentComparator data3{values3}; + + static const bool less_than12 = (data1 < data2); + static const bool less_than23 = (data2 < data3); + static const bool less_than21 = (data2 < data1); + static const bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data1{values1}; + static const Data data2{values2}; + static const Data data3{values3}; + + static const bool less_than_equal12 = (data1 <= data2); + static const bool less_than_equal23 = (data2 <= data3); + static const bool less_than_equal21 = (data2 <= data1); + static const bool less_than_equal32 = (data3 <= data2); + static const bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data1{values1}; + static const DataTransparentComparator data2{values2}; + static const DataTransparentComparator data3{values3}; + + static const bool less_than_equal12 = (data1 <= data2); + static const bool less_than_equal23 = (data2 <= data3); + static const bool less_than_equal21 = (data2 <= data1); + static const bool less_than_equal32 = (data3 <= data2); + static const bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data1{values1}; + static const Data data2{values2}; + static const Data data3{values3}; + + static const bool greater_than12 = (data1 > data2); + static const bool greater_than23 = (data2 > data3); + static const bool greater_than21 = (data2 > data1); + static const bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data1{values1}; + static const DataTransparentComparator data2{values2}; + static const DataTransparentComparator data3{values3}; + + static const bool greater_than12 = (data1 > data2); + static const bool greater_than23 = (data2 > data3); + static const bool greater_than21 = (data2 > data1); + static const bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const Data data1{values1}; + static const Data data2{values2}; + static const Data data3{values3}; + + static const bool greater_than_equal12 = (data1 >= data2); + static const bool greater_than_equal23 = (data2 >= data3); + static const bool greater_than_equal21 = (data2 >= data1); + static const bool greater_than_equal32 = (data3 >= data2); + static const bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal_with_transparent_comparator) + { + static const value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static const DataTransparentComparator data1{values1}; + static const DataTransparentComparator data2{values2}; + static const DataTransparentComparator data3{values3}; + + static const bool greater_than_equal12 = (data1 >= data2); + static const bool greater_than_equal23 = (data2 >= data3); + static const bool greater_than_equal21 = (data2 >= data1); + static const bool greater_than_equal32 = (data3 >= data2); + static const bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + }; +} diff --git a/test/test_const_set_ext_constexpr.cpp b/test/test_const_set_ext_constexpr.cpp new file mode 100644 index 00000000..feb15cc7 --- /dev/null +++ b/test/test_const_set_ext_constexpr.cpp @@ -0,0 +1,1570 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2025 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the 'Software'), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "unit_test_framework.h" + +#include +#include +#include +#include +#include +#include +#include + +#include "etl/const_set.h" +#include "etl/span.h" + +#include "data.h" + +namespace +{ + static constexpr size_t Max_Size = 10UL; + + //************************************************************************* + // The key type + //************************************************************************* + struct Key + { + // Default constructor + constexpr Key() + : k(0) + { + } + + // Construct from char key + constexpr explicit Key(char k_) + : k(k_) + { + } + + char k; + }; + + // Less-than operator for Key < Key + constexpr bool operator <(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k < rhs.k); + } + + // Less-than operator for Key < char + constexpr bool operator <(const Key& lhs, char rhs) noexcept + { + return (lhs.k < rhs); + } + + // Less-than operator for char < Key + constexpr bool operator <(char lhs, const Key& rhs) noexcept + { + return (lhs < rhs.k); + } + + // Equality operator for Key == Key + constexpr bool operator ==(const Key& lhs, const Key& rhs) noexcept + { + return (lhs.k == rhs.k); + } + + // Equality operator for Key != Key + constexpr bool operator !=(const Key& lhs, const Key& rhs) noexcept + { + return !(lhs.k == rhs.k); + } + + #define TEST_GREATER_THAN + #ifdef TEST_GREATER_THAN + using Data = etl::const_set_ext>; + using IData = etl::iconst_set>; + using DataTransparentComparator = etl::const_set_ext>; + using IDataTransparentComparator = etl::iconst_set>; + #else + using Data = etl::const_set_ext>; + using IData = etl::iconst_set>; + using DataTransparentComparator = etl::const_set_ext>; + using IDataTransparentComparator = etl::iconst_set>; + #endif + + using value_type = Data::value_type; + using key_type = Data::key_type; + using const_iterator = Data::const_iterator; + using span_type = etl::span; + + SUITE(test_const_set_ext_constexpr) + { + //************************************************************************* + TEST(test_default_constructor) + { + static constexpr Data data; + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 0UL); + CHECK_TRUE(empty); + CHECK_FALSE(full); + CHECK_TRUE(capacity == 0); + CHECK_TRUE(max_size == 0); + CHECK_TRUE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_min_size_from_span) + { + static constexpr value_type values[]{ Key('A') }; + static constexpr etl::span span(values); + static constexpr Data data{ span }; + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == 1U); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == span.size()); + CHECK_TRUE(max_size == span.size()); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size_from_span) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr span_type span(values); + static constexpr Data data{ span }; + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size_from_array) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr Data data{ values }; + + static constexpr bool is_valid = data.is_valid(); + static constexpr size_t size = data.size(); + static constexpr bool empty = data.empty(); + static constexpr bool full = data.full(); + static constexpr size_t capacity = data.capacity(); + static constexpr size_t max_size = data.max_size(); + static constexpr const_iterator begin = data.begin(); + static constexpr const_iterator end = data.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + + //************************************************************************* + TEST(test_constructor_max_size_status_from_iconst_set) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr Data data{ values }; + + static constexpr const IData& idata = data; + + static constexpr bool is_valid = idata.is_valid(); + static constexpr size_t size = idata.size(); + static constexpr bool empty = idata.empty(); + static constexpr bool full = idata.full(); + static constexpr size_t capacity = idata.capacity(); + static constexpr size_t max_size = idata.max_size(); + static constexpr const_iterator begin = idata.begin(); + static constexpr const_iterator end = idata.end(); + + CHECK_TRUE(is_valid); + CHECK_TRUE(size == Max_Size); + CHECK_FALSE(empty); + CHECK_TRUE(full); + CHECK_TRUE(capacity == Max_Size); + CHECK_TRUE(max_size == Max_Size); + CHECK_FALSE(begin == end); + } + +#if ETL_USING_CPP17 + //************************************************************************* + TEST(test_cpp17_deduced_constructor_from_span) + { + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr span_type span(values); + static constexpr etl::const_set_ext data{span}; + + etl::const_set check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } + + //************************************************************************* + TEST(test_cpp17_deduced_constructor_from_array) + { + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr etl::const_set_ext data{values}; + + etl::const_set check{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + CHECK_TRUE(data.is_valid()); + CHECK_TRUE(data.size() == Max_Size); + CHECK_FALSE(data.empty()); + CHECK_TRUE(data.full()); + CHECK_TRUE(data.capacity() == Max_Size); + CHECK_TRUE(data.max_size() == Max_Size); + CHECK_FALSE(data.begin() == data.end()); + } +#endif + + //************************************************************************* + TEST(test_begin) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr Data data{ values }; + + CHECK_TRUE(data.is_valid()); + static constexpr auto value = *data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(( Key('J')) == value); +#else + CHECK_TRUE(( Key('A')) == value); +#endif + } + + //************************************************************************* + TEST(test_end) + { + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; + + static constexpr Data data{ values }; + + static constexpr const_iterator end_itr = data.end(); + + CHECK_TRUE(end_itr == (data.begin() + data.size())); + } + + //************************************************************************* + TEST(test_equal_range) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr Data data{ values }; + + static constexpr ETL_OR_STD::pair resultA = data.equal_range(Key('A')); + static constexpr ETL_OR_STD::pair resultB = data.equal_range(Key('B')); + static constexpr ETL_OR_STD::pair resultC = data.equal_range(Key('C')); + static constexpr ETL_OR_STD::pair resultD = data.equal_range(Key('D')); + static constexpr ETL_OR_STD::pair resultE = data.equal_range(Key('E')); + static constexpr ETL_OR_STD::pair resultF = data.equal_range(Key('F')); + static constexpr ETL_OR_STD::pair resultG = data.equal_range(Key('G')); + static constexpr ETL_OR_STD::pair resultH = data.equal_range(Key('H')); + static constexpr ETL_OR_STD::pair resultI = data.equal_range(Key('I')); + static constexpr ETL_OR_STD::pair resultJ = data.equal_range(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_equal_range_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr DataTransparentComparator data{ values }; + + static constexpr ETL_OR_STD::pair resultA = data.equal_range('A'); + static constexpr ETL_OR_STD::pair resultB = data.equal_range('B'); + static constexpr ETL_OR_STD::pair resultC = data.equal_range('C'); + static constexpr ETL_OR_STD::pair resultD = data.equal_range('D'); + static constexpr ETL_OR_STD::pair resultE = data.equal_range('E'); + static constexpr ETL_OR_STD::pair resultF = data.equal_range('F'); + static constexpr ETL_OR_STD::pair resultG = data.equal_range('G'); + static constexpr ETL_OR_STD::pair resultH = data.equal_range('H'); + static constexpr ETL_OR_STD::pair resultI = data.equal_range('I'); + static constexpr ETL_OR_STD::pair resultJ = data.equal_range('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(10, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ.second))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA.first))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB.first))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC.first))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD.first))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE.first))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF.first))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG.first))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH.first))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI.first))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ.first))); + + CHECK_EQUAL(1, (std::distance(data.begin(), resultA.second))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB.second))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC.second))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultD.second))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE.second))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF.second))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultG.second))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultH.second))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultI.second))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultJ.second))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static constexpr Data data{ values }; + + static constexpr const_iterator resultA = data.lower_bound(Key('A')); + static constexpr const_iterator resultB = data.lower_bound(Key('B')); + static constexpr const_iterator resultC = data.lower_bound(Key('C')); + static constexpr const_iterator resultD = data.lower_bound(Key('D')); + static constexpr const_iterator resultE = data.lower_bound(Key('E')); + static constexpr const_iterator resultF = data.lower_bound(Key('F')); + static constexpr const_iterator resultG = data.lower_bound(Key('G')); + static constexpr const_iterator resultH = data.lower_bound(Key('H')); + static constexpr const_iterator resultI = data.lower_bound(Key('I')); + static constexpr const_iterator resultJ = data.lower_bound(Key('J')); + static constexpr const_iterator resultK = data.lower_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_lower_bound_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static constexpr DataTransparentComparator data{ values }; + + static constexpr const_iterator resultA = data.lower_bound('A'); + static constexpr const_iterator resultB = data.lower_bound('B'); + static constexpr const_iterator resultC = data.lower_bound('C'); + static constexpr const_iterator resultD = data.lower_bound('D'); + static constexpr const_iterator resultE = data.lower_bound('E'); + static constexpr const_iterator resultF = data.lower_bound('F'); + static constexpr const_iterator resultG = data.lower_bound('G'); + static constexpr const_iterator resultH = data.lower_bound('H'); + static constexpr const_iterator resultI = data.lower_bound('I'); + static constexpr const_iterator resultJ = data.lower_bound('J'); + static constexpr const_iterator resultK = data.lower_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static constexpr Data data{ values }; + + static constexpr const_iterator resultA = data.upper_bound(Key('A')); + static constexpr const_iterator resultB = data.upper_bound(Key('B')); + static constexpr const_iterator resultC = data.upper_bound(Key('C')); + static constexpr const_iterator resultD = data.upper_bound(Key('D')); + static constexpr const_iterator resultE = data.upper_bound(Key('E')); + static constexpr const_iterator resultF = data.upper_bound(Key('F')); + static constexpr const_iterator resultG = data.upper_bound(Key('G')); + static constexpr const_iterator resultH = data.upper_bound(Key('H')); + static constexpr const_iterator resultI = data.upper_bound(Key('I')); + static constexpr const_iterator resultJ = data.upper_bound(Key('J')); + static constexpr const_iterator resultK = data.upper_bound(Key('K')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_upper_bound_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('K'), Key('J'), Key('I'), Key('H'), Key('G'), + Key('F'), Key('E'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('E'), Key('F'), + Key('G'), Key('H'), Key('I'), Key('J'), Key('K') }; +#endif + + static constexpr DataTransparentComparator data{ values }; + + static constexpr const_iterator resultA = data.upper_bound('A'); + static constexpr const_iterator resultB = data.upper_bound('B'); + static constexpr const_iterator resultC = data.upper_bound('C'); + static constexpr const_iterator resultD = data.upper_bound('D'); + static constexpr const_iterator resultE = data.upper_bound('E'); + static constexpr const_iterator resultF = data.upper_bound('F'); + static constexpr const_iterator resultG = data.upper_bound('G'); + static constexpr const_iterator resultH = data.upper_bound('H'); + static constexpr const_iterator resultI = data.upper_bound('I'); + static constexpr const_iterator resultJ = data.upper_bound('J'); + static constexpr const_iterator resultK = data.upper_bound('K'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(10, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultK))); +#else + CHECK_EQUAL(1, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); + CHECK_EQUAL(10, (std::distance(data.begin(), resultK))); +#endif + } + + //************************************************************************* + TEST(test_count) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr Data data{ values }; + + static constexpr size_t countA = data.count(Key('A')); + static constexpr size_t countB = data.count(Key('B')); + static constexpr size_t countC = data.count(Key('C')); + static constexpr size_t countD = data.count(Key('D')); + static constexpr size_t countE = data.count(Key('E')); + static constexpr size_t countF = data.count(Key('F')); + static constexpr size_t countG = data.count(Key('G')); + static constexpr size_t countH = data.count(Key('H')); + static constexpr size_t countI = data.count(Key('I')); + static constexpr size_t countJ = data.count(Key('J')); + static constexpr size_t countK = data.count(Key('K')); + + CHECK_EQUAL(1, countA); + CHECK_EQUAL(1, countB); + CHECK_EQUAL(1, countC); + CHECK_EQUAL(1, countD); + CHECK_EQUAL(1, countE); + CHECK_EQUAL(1, countF); + CHECK_EQUAL(1, countG); + CHECK_EQUAL(1, countH); + CHECK_EQUAL(1, countI); + CHECK_EQUAL(1, countJ); + CHECK_EQUAL(0, countK); + } + + //************************************************************************* + TEST(test_count_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr DataTransparentComparator data{ values }; + + static constexpr size_t countA = data.count('A'); + static constexpr size_t countB = data.count('B'); + static constexpr size_t countC = data.count('C'); + static constexpr size_t countD = data.count('D'); + static constexpr size_t countE = data.count('E'); + static constexpr size_t countF = data.count('F'); + static constexpr size_t countG = data.count('G'); + static constexpr size_t countH = data.count('H'); + static constexpr size_t countI = data.count('I'); + static constexpr size_t countJ = data.count('J'); + static constexpr size_t countK = data.count('K'); + + CHECK_EQUAL(1, countA); + CHECK_EQUAL(1, countB); + CHECK_EQUAL(1, countC); + CHECK_EQUAL(1, countD); + CHECK_EQUAL(1, countE); + CHECK_EQUAL(1, countF); + CHECK_EQUAL(1, countG); + CHECK_EQUAL(1, countH); + CHECK_EQUAL(1, countI); + CHECK_EQUAL(1, countJ); + CHECK_EQUAL(0, countK); + } + + //************************************************************************* + TEST(test_const_iterator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr Data data{ values }; + + const_iterator itr = data.begin(); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE((Key('I')) == *itr++); + CHECK_TRUE((Key('H')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE(itr == data.end()); +#else + CHECK_TRUE((Key('A')) == *itr++); + CHECK_TRUE((Key('B')) == *itr++); + CHECK_TRUE((Key('C')) == *itr++); + CHECK_TRUE((Key('D')) == *itr++); + CHECK_TRUE((Key('E')) == *itr++); + CHECK_TRUE((Key('F')) == *itr++); + CHECK_TRUE((Key('G')) == *itr++); + CHECK_TRUE((Key('H')) == *itr++); + CHECK_TRUE((Key('I')) == *itr++); + CHECK_TRUE((Key('J')) == *itr++); + CHECK_TRUE(itr == data.end()); +#endif + } + + //************************************************************************* + TEST(test_find) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr Data data{ values }; + + static constexpr const_iterator resultA = data.find(Key('A')); + static constexpr const_iterator resultB = data.find(Key('B')); + static constexpr const_iterator resultC = data.find(Key('C')); + static constexpr const_iterator resultD = data.find(Key('D')); + static constexpr const_iterator resultE = data.find(Key('E')); + static constexpr const_iterator resultF = data.find(Key('F')); + static constexpr const_iterator resultG = data.find(Key('G')); + static constexpr const_iterator resultH = data.find(Key('H')); + static constexpr const_iterator resultI = data.find(Key('I')); + static constexpr const_iterator resultJ = data.find(Key('J')); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_find_using_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr DataTransparentComparator data{ values }; + + static constexpr const_iterator resultA = data.find('A'); + static constexpr const_iterator resultB = data.find('B'); + static constexpr const_iterator resultC = data.find('C'); + static constexpr const_iterator resultD = data.find('D'); + static constexpr const_iterator resultE = data.find('E'); + static constexpr const_iterator resultF = data.find('F'); + static constexpr const_iterator resultG = data.find('G'); + static constexpr const_iterator resultH = data.find('H'); + static constexpr const_iterator resultI = data.find('I'); + static constexpr const_iterator resultJ = data.find('J'); + +#ifdef TEST_GREATER_THAN + CHECK_EQUAL(9, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(0, (std::distance(data.begin(), resultJ))); +#else + CHECK_EQUAL(0, (std::distance(data.begin(), resultA))); + CHECK_EQUAL(1, (std::distance(data.begin(), resultB))); + CHECK_EQUAL(2, (std::distance(data.begin(), resultC))); + CHECK_EQUAL(3, (std::distance(data.begin(), resultD))); + CHECK_EQUAL(4, (std::distance(data.begin(), resultE))); + CHECK_EQUAL(5, (std::distance(data.begin(), resultF))); + CHECK_EQUAL(6, (std::distance(data.begin(), resultG))); + CHECK_EQUAL(7, (std::distance(data.begin(), resultH))); + CHECK_EQUAL(8, (std::distance(data.begin(), resultI))); + CHECK_EQUAL(9, (std::distance(data.begin(), resultJ))); +#endif + } + + //************************************************************************* + TEST(test_key_compare) + { + static constexpr Data data; + + static constexpr Data::key_compare compare = data.key_comp(); + + static constexpr Data::key_type a(Key('A')); + static constexpr Data::key_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_key_compare_using_transparent_comparator) + { + static constexpr DataTransparentComparator data; + static constexpr DataTransparentComparator::key_compare compare = data.key_comp(); + + static constexpr DataTransparentComparator::key_type a(Key('A')); + static constexpr DataTransparentComparator::key_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_value_compare) + { + static constexpr Data data; + static constexpr Data::value_compare compare = data.value_comp(); + + static constexpr Data::value_type a(Key('A')); + static constexpr Data::value_type b(Key('B')); + +#ifdef TEST_GREATER_THAN + CHECK(!compare(a, b)); + CHECK(compare(b, a)); +#else + CHECK(compare(a, b)); + CHECK(!compare(b, a)); +#endif + } + + //************************************************************************* + TEST(test_contains) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr Data data{ values }; + + static constexpr bool containsA = data.contains(Key('A')); + static constexpr bool containsB = data.contains(Key('B')); + static constexpr bool containsC = data.contains(Key('C')); + static constexpr bool containsD = data.contains(Key('D')); + static constexpr bool containsE = data.contains(Key('E')); + static constexpr bool containsF = data.contains(Key('F')); + static constexpr bool containsG = data.contains(Key('G')); + static constexpr bool containsH = data.contains(Key('H')); + static constexpr bool containsI = data.contains(Key('I')); + static constexpr bool containsJ = data.contains(Key('J')); + static constexpr bool containsK = data.contains(Key('K')); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_TRUE(containsH); + CHECK_TRUE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_contains_with_transparent_comparator) + { +#ifdef TEST_GREATER_THAN + static constexpr value_type values[]{ Key('J'), Key('I'), Key('H'), Key('G'), Key('F'), + Key('E'), Key('D'), Key('C'), Key('B'), Key('A') }; +#else + static constexpr value_type values[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; +#endif + + static constexpr DataTransparentComparator data{ values }; + + static constexpr bool containsA = data.contains('A'); + static constexpr bool containsB = data.contains('B'); + static constexpr bool containsC = data.contains('C'); + static constexpr bool containsD = data.contains('D'); + static constexpr bool containsE = data.contains('E'); + static constexpr bool containsF = data.contains('F'); + static constexpr bool containsG = data.contains('G'); + static constexpr bool containsH = data.contains('H'); + static constexpr bool containsI = data.contains('I'); + static constexpr bool containsJ = data.contains('J'); + static constexpr bool containsK = data.contains('K'); + + CHECK_TRUE(containsA); + CHECK_TRUE(containsB); + CHECK_TRUE(containsC); + CHECK_TRUE(containsD); + CHECK_TRUE(containsE); + CHECK_TRUE(containsF); + CHECK_TRUE(containsG); + CHECK_TRUE(containsH); + CHECK_TRUE(containsI); + CHECK_TRUE(containsJ); + CHECK_FALSE(containsK); + } + + //************************************************************************* + TEST(test_key_comp) + { + static constexpr Data data; + static constexpr Data::key_compare compare = data.key_comp(); + + static constexpr bool compareAA = compare(Key{ 'A' }, Key{ 'A' }); + static constexpr bool compareBA = compare(Key{ 'B' }, Key{ 'A' }); + static constexpr bool compareAB = compare(Key{ 'A' }, Key{ 'B' }); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); +#else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); +#endif + } + + //************************************************************************* + TEST(test_key_comp_transparent_comparator) + { + static constexpr DataTransparentComparator data; + static constexpr DataTransparentComparator::key_compare compare = data.key_comp(); + + static constexpr bool compareAA = compare('A', 'A'); + static constexpr bool compareBA = compare('B', 'A'); + static constexpr bool compareAB = compare('A', 'B'); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA); + CHECK_TRUE(compareBA); + CHECK_FALSE(compareAB); +#else + CHECK_FALSE(compareAA); + CHECK_FALSE(compareBA); + CHECK_TRUE(compareAB); +#endif + } + + //************************************************************************* + TEST(test_value_comp) + { + static constexpr Data data; + static constexpr Data::value_compare compare = data.value_comp(); + + static constexpr bool compareAA1 = compare( Key{ 'A' }, Key{ 'A' }); + static constexpr bool compareAA2 = compare( Key{ 'A' }, Key{ 'A' }); + static constexpr bool compareAA3 = compare(Key{ 'A' }, Key{ 'A' }); + + static constexpr bool compareBA1 = compare( Key{ 'B' }, Key{ 'A' }); + static constexpr bool compareBA2 = compare( Key{ 'B' }, Key{ 'A' }); + static constexpr bool compareBA3 = compare(Key{ 'B' }, Key{ 'A' }); + + static constexpr bool compareAB1 = compare( Key{ 'A' }, Key{ 'B' }); + static constexpr bool compareAB2 = compare( Key{ 'A' }, Key{ 'B' }); + static constexpr bool compareAB3 = compare(Key{ 'A' }, Key{ 'B' });; + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); +#else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); +#endif + } + + //************************************************************************* + TEST(test_value_comp_transparent_comparator) + { + static constexpr DataTransparentComparator data; + static constexpr DataTransparentComparator::value_compare compare = data.value_comp(); + + static constexpr bool compareAA1 = compare( 'A', 'A'); + static constexpr bool compareAA2 = compare( 'A', 'A'); + static constexpr bool compareAA3 = compare('A', 'A'); + + static constexpr bool compareBA1 = compare( 'B', 'A'); + static constexpr bool compareBA2 = compare( 'B', 'A'); + static constexpr bool compareBA3 = compare('B', 'A'); + + static constexpr bool compareAB1 = compare( 'A', 'B'); + static constexpr bool compareAB2 = compare( 'A', 'B'); + static constexpr bool compareAB3 = compare('A', 'B');; + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_TRUE(compareBA1); + CHECK_TRUE(compareBA2); + CHECK_TRUE(compareBA3); + + CHECK_FALSE(compareAB1); + CHECK_FALSE(compareAB2); + CHECK_FALSE(compareAB3); +#else + CHECK_FALSE(compareAA1); + CHECK_FALSE(compareAA2); + CHECK_FALSE(compareAA3); + + CHECK_FALSE(compareBA1); + CHECK_FALSE(compareBA2); + CHECK_FALSE(compareBA3); + + CHECK_TRUE(compareAB1); + CHECK_TRUE(compareAB2); + CHECK_TRUE(compareAB3); +#endif + } + + //************************************************************************* + TEST(test_equal) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J'), Key('K') }; + + static constexpr Data data1{values1}; + static constexpr Data data2{values2}; + static constexpr Data data3{values3}; + static constexpr Data data4{values4}; + + static constexpr bool equal12 = (data1 == data2); + static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_equal_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J'), Key('K') }; + + static constexpr DataTransparentComparator data1{values1}; + static constexpr DataTransparentComparator data2{values2}; + static constexpr DataTransparentComparator data3{values3}; + static constexpr DataTransparentComparator data4{values4}; + + static constexpr bool equal12 = (data1 == data2); + static constexpr bool equal13 = (data1 == data3); + static constexpr bool equal14 = (data1 == data4); + + CHECK_TRUE(equal12); + CHECK_FALSE(equal13); + CHECK_FALSE(equal14); + } + + //************************************************************************* + TEST(test_not_equal) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J'), Key('K') }; + + static constexpr Data data1{values1}; + static constexpr Data data2{values2}; + static constexpr Data data3{values3}; + static constexpr Data data4{values4}; + + static constexpr bool not_equal12 = (data1 != data2); + static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_not_equal_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J') }; + + static constexpr value_type values4[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('G'), Key('I'), Key('J'), Key('K') }; + + static constexpr DataTransparentComparator data1{values1}; + static constexpr DataTransparentComparator data2{values2}; + static constexpr DataTransparentComparator data3{values3}; + static constexpr DataTransparentComparator data4{values4}; + + static constexpr bool not_equal12 = (data1 != data2); + static constexpr bool not_equal13 = (data1 != data3); + static constexpr bool not_equal14 = (data1 != data4); + + CHECK_FALSE(not_equal12); + CHECK_TRUE(not_equal13); + CHECK_TRUE(not_equal14); + } + + //************************************************************************* + TEST(test_less_than) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data1{values1}; + static constexpr Data data2{values2}; + static constexpr Data data3{values3}; + + static constexpr bool less_than12 = (data1 < data2); + static constexpr bool less_than23 = (data2 < data3); + static constexpr bool less_than21 = (data2 < data1); + static constexpr bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data1{values1}; + static constexpr DataTransparentComparator data2{values2}; + static constexpr DataTransparentComparator data3{values3}; + + static constexpr bool less_than12 = (data1 < data2); + static constexpr bool less_than23 = (data2 < data3); + static constexpr bool less_than21 = (data2 < data1); + static constexpr bool less_than32 = (data3 < data2); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than12); + CHECK_FALSE(less_than23); + CHECK_TRUE(less_than21); + CHECK_TRUE(less_than32); +#else + CHECK_TRUE(less_than12); + CHECK_TRUE(less_than23); + CHECK_FALSE(less_than21); + CHECK_FALSE(less_than32); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data1{values1}; + static constexpr Data data2{values2}; + static constexpr Data data3{values3}; + + static constexpr bool less_than_equal12 = (data1 <= data2); + static constexpr bool less_than_equal23 = (data2 <= data3); + static constexpr bool less_than_equal21 = (data2 <= data1); + static constexpr bool less_than_equal32 = (data3 <= data2); + static constexpr bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_less_than_equal_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data1{values1}; + static constexpr DataTransparentComparator data2{values2}; + static constexpr DataTransparentComparator data3{values3}; + + static constexpr bool less_than_equal12 = (data1 <= data2); + static constexpr bool less_than_equal23 = (data2 <= data3); + static constexpr bool less_than_equal21 = (data2 <= data1); + static constexpr bool less_than_equal32 = (data3 <= data2); + static constexpr bool less_than_equal11 = (data1 <= data1); + +#ifdef TEST_GREATER_THAN + CHECK_FALSE(less_than_equal12); + CHECK_FALSE(less_than_equal23); + CHECK_TRUE(less_than_equal21); + CHECK_TRUE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#else + CHECK_TRUE(less_than_equal12); + CHECK_TRUE(less_than_equal23); + CHECK_FALSE(less_than_equal21); + CHECK_FALSE(less_than_equal32); + CHECK_TRUE(less_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data1{values1}; + static constexpr Data data2{values2}; + static constexpr Data data3{values3}; + + static constexpr bool greater_than12 = (data1 > data2); + static constexpr bool greater_than23 = (data2 > data3); + static constexpr bool greater_than21 = (data2 > data1); + static constexpr bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data1{values1}; + static constexpr DataTransparentComparator data2{values2}; + static constexpr DataTransparentComparator data3{values3}; + + static constexpr bool greater_than12 = (data1 > data2); + static constexpr bool greater_than23 = (data2 > data3); + static constexpr bool greater_than21 = (data2 > data1); + static constexpr bool greater_than32 = (data3 > data2); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than12); + CHECK_TRUE(greater_than23); + CHECK_FALSE(greater_than21); + CHECK_FALSE(greater_than32); +#else + CHECK_FALSE(greater_than12); + CHECK_FALSE(greater_than23); + CHECK_TRUE(greater_than21); + CHECK_TRUE(greater_than32); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr Data data1{values1}; + static constexpr Data data2{values2}; + static constexpr Data data3{values3}; + + static constexpr bool greater_than_equal12 = (data1 >= data2); + static constexpr bool greater_than_equal23 = (data2 >= data3); + static constexpr bool greater_than_equal21 = (data2 >= data1); + static constexpr bool greater_than_equal32 = (data3 >= data2); + static constexpr bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + + //************************************************************************* + TEST(test_greater_than_equal_with_transparent_comparator) + { + static constexpr value_type values1[]{ Key('A'), Key('B'), Key('B'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values2[]{ Key('A'), Key('B'), Key('C'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr value_type values3[]{ Key('A'), Key('B'), Key('D'), Key('D'), Key('E'), + Key('F'), Key('G'), Key('H'), Key('I'), Key('J') }; + + static constexpr DataTransparentComparator data1{values1}; + static constexpr DataTransparentComparator data2{values2}; + static constexpr DataTransparentComparator data3{values3}; + + static constexpr bool greater_than_equal12 = (data1 >= data2); + static constexpr bool greater_than_equal23 = (data2 >= data3); + static constexpr bool greater_than_equal21 = (data2 >= data1); + static constexpr bool greater_than_equal32 = (data3 >= data2); + static constexpr bool greater_than_equal11 = (data1 >= data1); + +#ifdef TEST_GREATER_THAN + CHECK_TRUE(greater_than_equal12); + CHECK_TRUE(greater_than_equal23); + CHECK_FALSE(greater_than_equal21); + CHECK_FALSE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#else + CHECK_FALSE(greater_than_equal12); + CHECK_FALSE(greater_than_equal23); + CHECK_TRUE(greater_than_equal21); + CHECK_TRUE(greater_than_equal32); + CHECK_TRUE(greater_than_equal11); +#endif + } + }; +} diff --git a/test/test_crc8_nrsc5.cpp b/test/test_crc8_nrsc5.cpp new file mode 100644 index 00000000..db109988 --- /dev/null +++ b/test/test_crc8_nrsc5.cpp @@ -0,0 +1,296 @@ +/****************************************************************************** +The MIT License(MIT) + +Embedded Template Library. +https://github.com/ETLCPP/etl +https://www.etlcpp.com + +Copyright(c) 2021 John Wellbelove + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files(the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and / or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions : + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. +******************************************************************************/ + +#include "unit_test_framework.h" + +#include +#include +#include +#include + +#include "etl/crc8_nrsc5.h" + +//***************************************************************************** +// The results for these tests were created from https://crccalc.com/ +//***************************************************************************** + +namespace +{ + SUITE(test_crc8_nrsc5) + { + //************************************************************************* + // Table size 4 + //************************************************************************* + TEST(test_crc8_nrsc5_4_constructor) + { + std::string data("123456789"); + + uint8_t crc = etl::crc8_nrsc5_t4(data.begin(), data.end()); + + CHECK_EQUAL(0xF7U, int(crc)); + } + +#if ETL_USING_CPP14 && !defined(ETL_CRC_FORCE_CPP03_IMPLEMENTATION) + //************************************************************************* + TEST(test_crc8_nrsc5_4_constructor_constexpr) + { + constexpr char data[] = "123456789"; + constexpr uint8_t crc = etl::crc8_nrsc5_t4(data, data + 9); + + CHECK_EQUAL(0xF7U, int(crc)); + } +#endif + + //************************************************************************* + TEST(test_crc8_nrsc5_4_add_values) + { + std::string data("123456789"); + + etl::crc8_nrsc5_t4 crc_calculator; + + for (size_t i = 0UL; i < data.size(); ++i) + { + crc_calculator.add(data[i]); + } + + uint8_t crc = crc_calculator; + + CHECK_EQUAL(0xF7U, int(crc)); + } + + //************************************************************************* + TEST(test_crc8_nrsc5_4_add_range) + { + std::string data("123456789"); + + etl::crc8_nrsc5_t4 crc_calculator; + + crc_calculator.add(data.begin(), data.end()); + + uint8_t crc = crc_calculator.value(); + + CHECK_EQUAL(0xF7U, int(crc)); + } + + //************************************************************************* + TEST(test_crc8_nrsc5_4_add_range_via_iterator) + { + std::string data("123456789"); + + etl::crc8_nrsc5_t4 crc_calculator; + + std::copy(data.begin(), data.end(), crc_calculator.input()); + + uint8_t crc = crc_calculator.value(); + + CHECK_EQUAL(0xF7U, int(crc)); + } + + //************************************************************************* + TEST(test_crc8_nrsc5_4_add_range_endian) + { + std::vector data1 = { 0x01U, 0x02U, 0x03U, 0x04U, 0x05U, 0x06U, 0x07U, 0x08U }; + std::vector data2 = { 0x04030201UL, 0x08070605UL }; + std::vector data3 = { 0x08U, 0x07U, 0x06U, 0x05U, 0x04U, 0x03U, 0x02U, 0x01U }; + + uint8_t crc1 = etl::crc8_nrsc5_t4(data1.begin(), data1.end()); + uint8_t crc2 = etl::crc8_nrsc5_t4((uint8_t*)&data2[0], (uint8_t*)(&data2[0] + data2.size())); + CHECK_EQUAL(int(crc1), int(crc2)); + + uint8_t crc3 = etl::crc8_nrsc5_t4(data3.rbegin(), data3.rend()); + CHECK_EQUAL(int(crc1), int(crc3)); + } + + //************************************************************************* + // Table size 16 + //************************************************************************* + TEST(test_crc8_nrsc5_16_constructor) + { + std::string data("123456789"); + + uint8_t crc = etl::crc8_nrsc5_t16(data.begin(), data.end()); + + CHECK_EQUAL(0xF7U, int(crc)); + } + +#if ETL_USING_CPP14 && !defined(ETL_CRC_FORCE_CPP03_IMPLEMENTATION) + //************************************************************************* + TEST(test_crc8_nrsc5_16_constructor_constexpr) + { + constexpr char data[] = "123456789"; + constexpr uint8_t crc = etl::crc8_nrsc5_t16(data, data + 9); + + CHECK_EQUAL(0xF7U, int(crc)); + } +#endif + + //************************************************************************* + TEST(test_crc8_nrsc5_16_add_values) + { + std::string data("123456789"); + + etl::crc8_nrsc5_t16 crc_calculator; + + for (size_t i = 0UL; i < data.size(); ++i) + { + crc_calculator.add(data[i]); + } + + uint8_t crc = crc_calculator; + + CHECK_EQUAL(0xF7U, int(crc)); + } + + //************************************************************************* + TEST(test_crc8_nrsc5_16_add_range) + { + std::string data("123456789"); + + etl::crc8_nrsc5_t16 crc_calculator; + + crc_calculator.add(data.begin(), data.end()); + + uint8_t crc = crc_calculator.value(); + + CHECK_EQUAL(0xF7U, int(crc)); + } + + //************************************************************************* + TEST(test_crc8_nrsc5_16_add_range_via_iterator) + { + std::string data("123456789"); + + etl::crc8_nrsc5_t16 crc_calculator; + + std::copy(data.begin(), data.end(), crc_calculator.input()); + + uint8_t crc = crc_calculator.value(); + + CHECK_EQUAL(0xF7U, int(crc)); + } + + //************************************************************************* + TEST(test_crc8_nrsc5_16_add_range_endian) + { + std::vector data1 = { 0x01U, 0x02U, 0x03U, 0x04U, 0x05U, 0x06U, 0x07U, 0x08U }; + std::vector data2 = { 0x04030201UL, 0x08070605UL }; + std::vector data3 = { 0x08U, 0x07U, 0x06U, 0x05U, 0x04U, 0x03U, 0x02U, 0x01U }; + + uint8_t crc1 = etl::crc8_nrsc5_t16(data1.begin(), data1.end()); + uint8_t crc2 = etl::crc8_nrsc5_t16((uint8_t*)&data2[0], (uint8_t*)(&data2[0] + data2.size())); + CHECK_EQUAL(int(crc1), int(crc2)); + + uint8_t crc3 = etl::crc8_nrsc5_t16(data3.rbegin(), data3.rend()); + CHECK_EQUAL(int(crc1), int(crc3)); + } + + //************************************************************************* + // Table size 256 + //************************************************************************* + TEST(test_crc8_nrsc5_256_constructor) + { + std::string data("123456789"); + + uint8_t crc = etl::crc8_nrsc5(data.begin(), data.end()); + + CHECK_EQUAL(0xF7U, int(crc)); + } + +#if ETL_USING_CPP14 && !defined(ETL_CRC_FORCE_CPP03_IMPLEMENTATION) + //************************************************************************* + TEST(test_crc8_nrsc5_256_constructor_constexpr) + { + constexpr char data[] = "123456789"; + constexpr uint8_t crc = etl::crc8_nrsc5(data, data + 9); + + CHECK_EQUAL(0xF7U, int(crc)); + } +#endif + + //************************************************************************* + TEST(test_crc8_nrsc5_256_add_values) + { + std::string data("123456789"); + + etl::crc8_nrsc5 crc_calculator; + + for (size_t i = 0UL; i < data.size(); ++i) + { + crc_calculator.add(data[i]); + } + + uint8_t crc = crc_calculator; + + CHECK_EQUAL(0xF7U, int(crc)); + } + + //************************************************************************* + TEST(test_crc8_nrsc5_256_add_range) + { + std::string data("123456789"); + + etl::crc8_nrsc5 crc_calculator; + + crc_calculator.add(data.begin(), data.end()); + + uint8_t crc = crc_calculator.value(); + + CHECK_EQUAL(0xF7U, int(crc)); + } + + //************************************************************************* + TEST(test_crc8_nrsc5_256_add_range_via_iterator) + { + std::string data("123456789"); + + etl::crc8_nrsc5 crc_calculator; + + std::copy(data.begin(), data.end(), crc_calculator.input()); + + uint8_t crc = crc_calculator.value(); + + CHECK_EQUAL(0xF7U, int(crc)); + } + + //************************************************************************* + TEST(test_crc8_nrsc5_256_add_range_endian) + { + std::vector data1 = { 0x01U, 0x02U, 0x03U, 0x04U, 0x05U, 0x06U, 0x07U, 0x08U }; + std::vector data2 = { 0x04030201UL, 0x08070605UL }; + std::vector data3 = { 0x08U, 0x07U, 0x06U, 0x05U, 0x04U, 0x03U, 0x02U, 0x01U }; + + uint8_t crc1 = etl::crc8_nrsc5(data1.begin(), data1.end()); + uint8_t crc2 = etl::crc8_nrsc5((uint8_t*)&data2[0], (uint8_t*)(&data2[0] + data2.size())); + CHECK_EQUAL(int(crc1), int(crc2)); + + uint8_t crc3 = etl::crc8_nrsc5(data3.rbegin(), data3.rend()); + CHECK_EQUAL(int(crc1), int(crc3)); + } + }; +} + diff --git a/test/test_multiset.cpp b/test/test_multiset.cpp index cb64956c..aae2b234 100644 --- a/test/test_multiset.cpp +++ b/test/test_multiset.cpp @@ -45,13 +45,13 @@ static const size_t MAX_SIZE = 10UL; #define TEST_GREATER_THAN #ifdef TEST_GREATER_THAN -using Data = etl::multiset>; -using IData = etl::imultiset>; -using Compare_Data = std::multiset>; + using Data = etl::multiset>; + using IData = etl::imultiset>; + using Compare_Data = std::multiset>; #else -using Data = etl::multiset>; -using IData = etl::multiset>; -using Compare_Data = std::multiset>; + using Data = etl::multiset>; + using IData = etl::imultiset>; + using Compare_Data = std::multiset>; #endif using ItemM = TestDataM; @@ -1151,30 +1151,17 @@ namespace CHECK_EQUAL(*i_compare, *i_data); #ifdef TEST_GREATER_THAN - i_compare = compare_data.lower_bound(-1); - CHECK(compare_data.end() == i_compare); - i_data = data.lower_bound(-1); CHECK(data.end() == i_data); - i_compare = compare_data.lower_bound(99); i_data = data.lower_bound(99); - CHECK(i_data != data.end()); - - if ((i_data != data.end()) && (i_compare != compare_data.end())) - { - CHECK(*i_compare == *i_data); - } + CHECK(i_data == data.begin()); #else - i_compare = compare_data.lower_bound(-1); i_data = data.lower_bound(-1); - CHECK_EQUAL(*i_compare, *i_data); - - i_compare = compare_data.lower_bound(99); - CHECK_EQUAL(compare_data.end(), i_compare); + CHECK(data.begin() == i_data); i_data = data.lower_bound(99); - CHECK_EQUAL(data.end(), i_data); + CHECK(i_data == data.end()); #endif } @@ -1213,30 +1200,17 @@ namespace CHECK_EQUAL(*i_compare, *i_data); #ifdef TEST_GREATER_THAN - i_compare = compare_data.lower_bound(-1); - CHECK(compare_data.end() == i_compare); - i_data = data.lower_bound(-1); CHECK(data.end() == i_data); - i_compare = compare_data.lower_bound(99); i_data = data.lower_bound(99); - CHECK(i_data != data.end()); - - if ((i_data != data.end()) && (i_compare != compare_data.end())) - { - CHECK(*i_compare == *i_data); - } + CHECK(i_data == data.begin()); #else - i_compare = compare_data.lower_bound(-1); i_data = data.lower_bound(-1); - CHECK_EQUAL(*i_compare, *i_data); - - i_compare = compare_data.lower_bound(99); - CHECK_EQUAL(compare_data.end(), i_compare); + CHECK(data.begin() == i_data); i_data = data.lower_bound(99); - CHECK_EQUAL(data.end(), i_data); + CHECK(i_data == data.end()); #endif } @@ -1275,30 +1249,17 @@ namespace CHECK_EQUAL(*i_compare, *i_data); #ifdef TEST_GREATER_THAN - i_compare = compare_data.upper_bound(-1); - CHECK(compare_data.end() == i_compare); - i_data = data.upper_bound(-1); CHECK(data.end() == i_data); - i_compare = compare_data.upper_bound(99); i_data = data.upper_bound(99); - CHECK(i_data != data.end()); - - if ((i_data != data.end()) && (i_compare != compare_data.end())) - { - CHECK(*i_compare == *i_data); - } + CHECK(i_data == data.begin()); #else - i_compare = compare_data.upper_bound(-1); i_data = data.upper_bound(-1); - CHECK_EQUAL(*i_compare, *i_data); - - i_compare = compare_data.upper_bound(99); - CHECK_EQUAL(compare_data.end(), i_compare); + CHECK(data.begin() == i_data); i_data = data.upper_bound(99); - CHECK_EQUAL(data.end(), i_data); + CHECK(i_data == data.end()); #endif } @@ -1337,30 +1298,17 @@ namespace CHECK_EQUAL(*i_compare, *i_data); #ifdef TEST_GREATER_THAN - i_compare = compare_data.upper_bound(-1); - CHECK(compare_data.end() == i_compare); - i_data = data.upper_bound(-1); CHECK(data.end() == i_data); - i_compare = compare_data.upper_bound(99); i_data = data.upper_bound(99); - CHECK(i_data != data.end()); - - if ((i_data != data.end()) && (i_compare != compare_data.end())) - { - CHECK(*i_compare == *i_data); - } + CHECK(i_data == data.begin()); #else - i_compare = compare_data.upper_bound(-1); i_data = data.upper_bound(-1); - CHECK_EQUAL(*i_compare, *i_data); - - i_compare = compare_data.upper_bound(99); - CHECK_EQUAL(compare_data.end(), i_compare); + CHECK(data.begin() == i_data); i_data = data.upper_bound(99); - CHECK_EQUAL(data.end(), i_data); + CHECK(i_data == data.end()); #endif } diff --git a/test/test_set.cpp b/test/test_set.cpp index a8d93776..0865eff8 100644 --- a/test/test_set.cpp +++ b/test/test_set.cpp @@ -1025,30 +1025,17 @@ namespace CHECK_EQUAL(*i_compare, *i_data); #ifdef TEST_GREATER_THAN - i_compare = compare_data.lower_bound(-1); - CHECK(compare_data.end() == i_compare); - i_data = data.lower_bound(-1); CHECK(data.end() == i_data); - i_compare = compare_data.lower_bound(11); - i_data = data.lower_bound(11); - CHECK(i_data != data.end()); - - if ((i_data != data.end()) && (i_compare != compare_data.end())) - { - CHECK(*i_compare == *i_data); - } + i_data = data.lower_bound(99); + CHECK(i_data == data.begin()); #else - i_compare = compare_data.lower_bound(-1); i_data = data.lower_bound(-1); - CHECK_EQUAL(*i_compare, *i_data); + CHECK(data.begin() == i_data); - i_compare = compare_data.lower_bound(11); - CHECK_EQUAL(compare_data.end(), i_compare); - - i_data = data.lower_bound(11); - CHECK_EQUAL(data.end(), i_data); + i_data = data.lower_bound(99); + CHECK(i_data == data.end()); #endif } @@ -1087,25 +1074,17 @@ namespace CHECK_EQUAL(*i_compare, *i_data); #ifdef TEST_GREATER_THAN - i_compare = compare_data.lower_bound(-1); - CHECK(compare_data.end() == i_compare); - i_data = data.lower_bound(-1); CHECK(data.end() == i_data); - i_compare = compare_data.lower_bound(11); - i_data = data.lower_bound(11); - CHECK_EQUAL(*i_compare, *i_data); + i_data = data.lower_bound(99); + CHECK(i_data == data.begin()); #else - i_compare = compare_data.lower_bound(-1); i_data = data.lower_bound(-1); - CHECK_EQUAL(*i_compare, *i_data); + CHECK(data.begin() == i_data); - i_compare = compare_data.lower_bound(11); - CHECK_EQUAL(compare_data.end(), i_compare); - - i_data = data.lower_bound(11); - CHECK_EQUAL(data.end(), i_data); + i_data = data.lower_bound(99); + CHECK(i_data == data.end()); #endif } @@ -1144,25 +1123,17 @@ namespace CHECK_EQUAL(*i_compare, *i_data); #ifdef TEST_GREATER_THAN - i_compare = compare_data.upper_bound(-1); - CHECK(compare_data.end() == i_compare); - i_data = data.upper_bound(-1); CHECK(data.end() == i_data); - i_compare = compare_data.upper_bound(11); - i_data = data.upper_bound(11); - CHECK_EQUAL(*i_compare, *i_data); + i_data = data.upper_bound(99); + CHECK(i_data == data.begin()); #else - i_compare = compare_data.upper_bound(-1); i_data = data.upper_bound(-1); - CHECK_EQUAL(*i_compare, *i_data); + CHECK(data.begin() == i_data); - i_compare = compare_data.upper_bound(11); - CHECK_EQUAL(compare_data.end(), i_compare); - - i_data = data.upper_bound(11); - CHECK_EQUAL(data.end(), i_data); + i_data = data.upper_bound(99); + CHECK(i_data == data.end()); #endif } @@ -1201,25 +1172,17 @@ namespace CHECK_EQUAL(*i_compare, *i_data); #ifdef TEST_GREATER_THAN - i_compare = compare_data.upper_bound(-1); - CHECK(compare_data.end() == i_compare); - i_data = data.upper_bound(-1); CHECK(data.end() == i_data); - i_compare = compare_data.upper_bound(11); - i_data = data.upper_bound(11); - CHECK_EQUAL(*i_compare, *i_data); + i_data = data.upper_bound(99); + CHECK(i_data == data.begin()); #else - i_compare = compare_data.upper_bound(-1); i_data = data.upper_bound(-1); - CHECK_EQUAL(*i_compare, *i_data); + CHECK(data.begin() == i_data); - i_compare = compare_data.upper_bound(11); - CHECK_EQUAL(compare_data.end(), i_compare); - - i_data = data.upper_bound(11); - CHECK_EQUAL(data.end(), i_data); + i_data = data.upper_bound(99); + CHECK(i_data == data.end()); #endif } diff --git a/test/vs2022/etl.vcxproj b/test/vs2022/etl.vcxproj index 70151e9f..136e2d03 100644 --- a/test/vs2022/etl.vcxproj +++ b/test/vs2022/etl.vcxproj @@ -3294,6 +3294,8 @@ + + @@ -3343,6 +3345,7 @@ + @@ -9300,6 +9303,14 @@ + + + + + + + + @@ -9349,6 +9360,7 @@ + diff --git a/test/vs2022/etl.vcxproj.filters b/test/vs2022/etl.vcxproj.filters index d7d77829..9a8d6339 100644 --- a/test/vs2022/etl.vcxproj.filters +++ b/test/vs2022/etl.vcxproj.filters @@ -1518,6 +1518,15 @@ ETL\Utilities + + ETL\Containers + + + ETL\Containers + + + ETL\Maths\CRC + @@ -3629,6 +3638,33 @@ Tests\Containers + + Tests\Containers + + + Tests\Containers + + + Tests\Containers + + + Tests\Containers + + + Tests\Containers + + + Tests\Containers + + + Tests\Containers + + + Tests\Containers + + + Tests\CRC +