Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-07-30 08:46:18

0001 /*
0002     Copyright (c) 2005-2021 Intel Corporation
0003 
0004     Licensed under the Apache License, Version 2.0 (the "License");
0005     you may not use this file except in compliance with the License.
0006     You may obtain a copy of the License at
0007 
0008         http://www.apache.org/licenses/LICENSE-2.0
0009 
0010     Unless required by applicable law or agreed to in writing, software
0011     distributed under the License is distributed on an "AS IS" BASIS,
0012     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
0013     See the License for the specific language governing permissions and
0014     limitations under the License.
0015 */
0016 
0017 #ifndef __TBB_detail__hash_compare_H
0018 #define __TBB_detail__hash_compare_H
0019 
0020 #include <functional>
0021 
0022 #include "_containers_helpers.h"
0023 
0024 namespace tbb {
0025 namespace detail {
0026 namespace d1 {
0027 
0028 template <typename Key, typename Hash, typename KeyEqual>
0029 class hash_compare {
0030     using is_transparent_hash = has_transparent_key_equal<Key, Hash, KeyEqual>;
0031 public:
0032     using hasher = Hash;
0033     using key_equal = typename is_transparent_hash::type;
0034 
0035     hash_compare() = default;
0036     hash_compare( hasher hash, key_equal equal ) : my_hasher(hash), my_equal(equal) {}
0037 
0038     std::size_t operator()( const Key& key ) const {
0039         return std::size_t(my_hasher(key));
0040     }
0041 
0042     bool operator()( const Key& key1, const Key& key2 ) const {
0043         return my_equal(key1, key2);
0044     }
0045 
0046     template <typename K, typename = typename std::enable_if<is_transparent_hash::value, K>::type>
0047     std::size_t operator()( const K& key ) const {
0048         return std::size_t(my_hasher(key));
0049     }
0050 
0051     template <typename K1, typename K2, typename = typename std::enable_if<is_transparent_hash::value, K1>::type>
0052     bool operator()( const K1& key1, const K2& key2 ) const {
0053         return my_equal(key1, key2);
0054     }
0055 
0056     hasher hash_function() const {
0057         return my_hasher;
0058     }
0059 
0060     key_equal key_eq() const {
0061         return my_equal;
0062     }
0063 
0064 
0065 private:
0066     hasher my_hasher;
0067     key_equal my_equal;
0068 }; // class hash_compare
0069 
0070 //! hash_compare that is default argument for concurrent_hash_map
0071 template <typename Key>
0072 class tbb_hash_compare {
0073 public:
0074     std::size_t hash( const Key& a ) const { return my_hash_func(a); }
0075 #if defined(_MSC_VER) && _MSC_VER <= 1900
0076 #pragma warning (push)
0077 // MSVC 2015 throws a strange warning: 'std::size_t': forcing value to bool 'true' or 'false'
0078 #pragma warning (disable: 4800)
0079 #endif
0080     bool equal( const Key& a, const Key& b ) const { return my_key_equal(a, b); }
0081 #if defined(_MSC_VER) && _MSC_VER <= 1900
0082 #pragma warning (pop)
0083 #endif
0084 private:
0085     std::hash<Key> my_hash_func;
0086     std::equal_to<Key> my_key_equal;
0087 };
0088 
0089 } // namespace d1
0090 #if __TBB_CPP20_CONCEPTS_PRESENT
0091 inline namespace d0 {
0092 
0093 template <typename HashCompare, typename Key>
0094 concept hash_compare = std::copy_constructible<HashCompare> &&
0095                        requires( const std::remove_reference_t<HashCompare>& hc, const Key& key1, const Key& key2 ) {
0096                            { hc.hash(key1) } -> std::same_as<std::size_t>;
0097                            { hc.equal(key1, key2) } -> std::convertible_to<bool>;
0098                        };
0099 
0100 } // namespace d0
0101 #endif // __TBB_CPP20_CONCEPTS_PRESENT
0102 } // namespace detail
0103 } // namespace tbb
0104 
0105 #if TBB_DEFINE_STD_HASH_SPECIALIZATIONS
0106 
0107 namespace std {
0108 
0109 template <typename T, typename U>
0110 struct hash<std::pair<T, U>> {
0111 public:
0112     std::size_t operator()( const std::pair<T, U>& p ) const {
0113         return first_hash(p.first) ^ second_hash(p.second);
0114     }
0115 
0116 private:
0117     std::hash<T> first_hash;
0118     std::hash<U> second_hash;
0119 }; // struct hash<std::pair>
0120 
0121 // Apple clang and MSVC defines their own specializations for std::hash<std::basic_string<T, Traits, Alloc>>
0122 #if !(_LIBCPP_VERSION) && !(_CPPLIB_VER)
0123 
0124 template <typename CharT, typename Traits, typename Allocator>
0125 struct hash<std::basic_string<CharT, Traits, Allocator>> {
0126 public:
0127     std::size_t operator()( const std::basic_string<CharT, Traits, Allocator>& s ) const {
0128         std::size_t h = 0;
0129         for ( const CharT* c = s.c_str(); *c; ++c ) {
0130             h = h * hash_multiplier ^ char_hash(*c);
0131         }
0132         return h;
0133     }
0134 
0135 private:
0136     static constexpr std::size_t hash_multiplier = tbb::detail::select_size_t_constant<2654435769U, 11400714819323198485ULL>::value;
0137 
0138     std::hash<CharT> char_hash;
0139 }; // struct hash<std::basic_string>
0140 
0141 #endif // !(_LIBCPP_VERSION || _CPPLIB_VER)
0142 
0143 } // namespace std
0144 
0145 #endif // TBB_DEFINE_STD_HASH_SPECIALIZATIONS
0146 
0147 #endif // __TBB_detail__hash_compare_H