mirror of
https://github.com/greg7mdp/parallel-hashmap.git
synced 2026-08-29 08:34:39 +08:00
Add default hash for std::pair and std::tuple... slight code reorganization.
This commit is contained in:
Vendored
+3
-1
@@ -47,9 +47,9 @@
|
||||
#include <cassert>
|
||||
#include <atomic>
|
||||
|
||||
#include "phmap_fwd_decl.h"
|
||||
#include "phmap_utils.h"
|
||||
#include "phmap_base.h"
|
||||
#include "phmap_fwd_decl.h"
|
||||
|
||||
#if PHMAP_HAVE_STD_STRING_VIEW
|
||||
#include <string_view>
|
||||
@@ -4047,6 +4047,7 @@ struct HashEq<std::wstring_view> : StringHashEqT<wchar_t> {};
|
||||
#endif
|
||||
|
||||
// Supports heterogeneous lookup for pointers and smart pointers.
|
||||
// -------------------------------------------------------------
|
||||
template <class T>
|
||||
struct HashEq<T*>
|
||||
{
|
||||
@@ -4068,6 +4069,7 @@ struct HashEq<T*>
|
||||
|
||||
private:
|
||||
static const T* ToPtr(const T* ptr) { return ptr; }
|
||||
|
||||
template <class U, class D>
|
||||
static const T* ToPtr(const std::unique_ptr<U, D>& ptr) {
|
||||
return ptr.get();
|
||||
|
||||
Vendored
+9
-5
@@ -14,9 +14,18 @@
|
||||
#include <memory>
|
||||
#include <utility>
|
||||
|
||||
#if defined(PHMAP_USE_ABSL_HASH)
|
||||
namespace absl { template <class T> struct Hash; };
|
||||
#endif
|
||||
|
||||
namespace phmap {
|
||||
|
||||
#if defined(PHMAP_USE_ABSL_HASH)
|
||||
template <class T> using Hash = absl::Hash<T>;
|
||||
#else
|
||||
template <class T> struct Hash;
|
||||
#endif
|
||||
|
||||
template <class T> struct EqualTo;
|
||||
template <class T> using Allocator = typename std::allocator<T>;
|
||||
template<class T1, class T2> using Pair = typename std::pair<T1, T2>;
|
||||
@@ -29,13 +38,8 @@ namespace phmap {
|
||||
template <class T, class E = void>
|
||||
struct HashEq
|
||||
{
|
||||
#if defined(PHMAP_USE_ABSL_HASHEQ)
|
||||
using Hash = absl::Hash<T>;
|
||||
using Eq = phmap::EqualTo<T>;
|
||||
#else
|
||||
using Hash = phmap::Hash<T>;
|
||||
using Eq = phmap::EqualTo<T>;
|
||||
#endif
|
||||
};
|
||||
|
||||
template <class T>
|
||||
|
||||
Vendored
+50
-3
@@ -23,6 +23,7 @@
|
||||
|
||||
#include <cstdint>
|
||||
#include <functional>
|
||||
#include <tuple>
|
||||
#include "phmap_bits.h"
|
||||
|
||||
namespace phmap
|
||||
@@ -122,7 +123,11 @@ private:
|
||||
public:
|
||||
static constexpr bool value = std::is_same<decltype(test<T>(0)), yes>::value;
|
||||
};
|
||||
|
||||
|
||||
#if defined(PHMAP_USE_ABSL_HASH) && !defined(phmap_fwd_decl_h_guard_)
|
||||
namespace absl { template <class T> struct Hash; };
|
||||
template <class T> using Hash = absl::Hash<T>;
|
||||
#else
|
||||
// ---------------------------------------------------------------
|
||||
// phmap::Hash
|
||||
// ---------------------------------------------------------------
|
||||
@@ -264,6 +269,8 @@ struct Hash<double> : public phmap_unary_function<double, size_t>
|
||||
}
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
template <class H, int sz> struct Combiner
|
||||
{
|
||||
H operator()(H seed, size_t value);
|
||||
@@ -285,7 +292,7 @@ template <class H> struct Combiner<H, 8>
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// define HashState to combine member hashes... see example below
|
||||
// -----------------------------------------------------------------------------
|
||||
template <typename H>
|
||||
class HashStateBase {
|
||||
@@ -301,11 +308,51 @@ template <typename T, typename... Ts>
|
||||
H HashStateBase<H>::combine(H seed, const T& v, const Ts&... vs)
|
||||
{
|
||||
return HashStateBase<H>::combine(Combiner<H, sizeof(H)>()(
|
||||
seed, phmap::Hash<T>()(v)), vs...);
|
||||
seed, phmap::Hash<T>()(v)),
|
||||
vs...);
|
||||
}
|
||||
|
||||
using HashState = HashStateBase<size_t>;
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
#if !defined(PHMAP_USE_ABSL_HASH)
|
||||
|
||||
// define Hash for std::pair
|
||||
// -------------------------
|
||||
template<class T1, class T2>
|
||||
struct Hash<std::pair<T1, T2>> {
|
||||
size_t operator()(std::pair<T1, T2> const& p) const noexcept {
|
||||
return phmap::HashState().combine(0, p.first, p.second);
|
||||
}
|
||||
};
|
||||
|
||||
// define Hash for std::tuple
|
||||
// --------------------------
|
||||
template<class... T>
|
||||
struct Hash<std::tuple<T...>> {
|
||||
size_t operator()(std::tuple<T...> const& t) const noexcept {
|
||||
return _hash_helper(t);
|
||||
}
|
||||
|
||||
private:
|
||||
template<size_t I = 0, class ...P>
|
||||
typename std::enable_if<I == sizeof...(P), size_t>::type
|
||||
_hash_helper(const std::tuple<P...> &) const noexcept { return 0; }
|
||||
|
||||
template<size_t I = 0, class ...P>
|
||||
typename std::enable_if<I < sizeof...(P), size_t>::type
|
||||
_hash_helper(const std::tuple<P...> &t) const noexcept {
|
||||
const auto &el = std::get<I>(t);
|
||||
using el_type = std::remove_cv<std::remove_reference<decltype(el)>::type>::type;
|
||||
return phmap::Hash<el_type>()(el) + _hash_helper<I + 1>(t);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
} // namespace phmap
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user