From 6ae6e2ee495a0b052f63809e23f456f0ec889382 Mon Sep 17 00:00:00 2001 From: sunkaicheng Date: Tue, 20 Aug 2019 00:48:22 +0800 Subject: [PATCH] only support dump&load is_trivially_copyable types --- examples/dump_load.cc | 1 + parallel_hashmap/phmap.h | 72 +++++----------------------------- parallel_hashmap/phmap_base.h | 25 ++++-------- parallel_hashmap/phmap_utils.h | 43 ++++++-------------- tests/dump_load_test.cc | 5 ++- 5 files changed, 34 insertions(+), 112 deletions(-) diff --git a/examples/dump_load.cc b/examples/dump_load.cc index bec9e48..4c92113 100644 --- a/examples/dump_load.cc +++ b/examples/dump_load.cc @@ -55,3 +55,4 @@ int main() dump_load_parallel_flat_hash_map(); return 0; } + diff --git a/parallel_hashmap/phmap.h b/parallel_hashmap/phmap.h index de42395..05e8b25 100644 --- a/parallel_hashmap/phmap.h +++ b/parallel_hashmap/phmap.h @@ -1538,7 +1538,7 @@ public: } template - typename std::enable_if::value, bool>::type + typename std::enable_if::value, bool>::type dump(OutputArchive& ar) { typename OutputArchive::Guard guard(&ar); if (!ar.dump(size_)) { @@ -1547,7 +1547,7 @@ public: } if (size_ == 0) { return true; - } + } if (!ar.dump(capacity_)) { std::cerr << "Failed to dump capacity_" << std::endl; return false; @@ -1561,12 +1561,12 @@ public: if (!ar.dump(reinterpret_cast(slots_), sizeof(slot_type) * capacity_)) { std::cerr << "Failed to dump slot_" << std::endl; return false; - } + } return true; } template - typename std::enable_if::value, bool>::type + typename std::enable_if::value, bool>::type load(InputArchive& ar) { typename InputArchive::Guard guard(&ar); if (!ar.load(&size_)){ @@ -1594,60 +1594,6 @@ public: return true; } - // V will be V for hash_set and std::pair for hash_map - template - typename std::enable_if::value - && type_traits_internal::IsStringOrArithmeticType::value, bool>::type - dump(OutputArchive& ar) { - typename OutputArchive::Guard guard(&ar); - if (!ar.template dump(size_)) { - std::cerr << "Failed to dump size" << std::endl; - return false; - } - if (size_ == 0) { - return true; - } - for (auto it = this->begin(); it != this->end(); ++it) { - if (!ar.template dump(*it)) { - std::cerr << "Failed to dump element" << std::endl; - return false; - } - } - return true; - } - - template - typename std::enable_if::value - && type_traits_internal::IsStringOrArithmeticType::value, bool>::type - load(InputArchive& ar) { - typename InputArchive::Guard guard(&ar); - size_t sz = 0; - ar.template load(&sz); - for (size_t i = 0; i < sz; i ++) { - V v; - if (!ar.template load(&v)) { - std::cerr << "Failed to load element " << i << std::endl; - return false; - } - this->insert(v); - } - return true; - } - - template - typename std::enable_if::value, bool>::type - dump(OutputArchive&) { - std::cerr << "Does not support this type now!" << std::endl; - return false; - } - - template - typename std::enable_if::value, bool>::type - load(InputArchive&) { - std::cerr << "Does not support this type now!" << std::endl; - return false; - } - void rehash(size_t n) { if (n == 0 && capacity_ == 0) return; if (n == 0 && size_ == 0) { @@ -3253,8 +3199,9 @@ public: a.swap(b); } - template - bool dump(OutputArchiveWrapper& w) { + template + typename std::enable_if::value, bool>::type + dump(OutputArchiveWrapper& w) { for (size_t i = 0; i < sets_.size(); ++i) { auto& inner = sets_[i]; auto ar = w.create_archive(i); @@ -3272,8 +3219,9 @@ public: return true; } - template - bool load(InputArchiveWrapper& w) { + template + typename std::enable_if::value, bool>::type + load(InputArchiveWrapper& w) { size_t submap_count = w.load_meta(); if (submap_count != subcnt()) { diff --git a/parallel_hashmap/phmap_base.h b/parallel_hashmap/phmap_base.h index 8f03623..82a38b0 100644 --- a/parallel_hashmap/phmap_base.h +++ b/parallel_hashmap/phmap_base.h @@ -78,27 +78,16 @@ struct PairTrait : public std::false_type { template struct PairTrait>: public std::true_type { - using first_type = typename std::remove_cv::type; - using second_type = typename std::remove_cv::type; + using first_type = T1; + using second_type = T2; }; template -struct IsArithmeticType { - static constexpr bool value = std::is_arithmetic::value - || (PairTrait::value && - std::is_arithmetic::first_type>::value - && std::is_arithmetic::second_type>::value); -}; - -template -struct IsStringOrArithmeticType { - static constexpr bool value = IsArithmeticType::value - || std::is_same::value - || (PairTrait::value - && (std::is_arithmetic::first_type>::value - || std::is_same::first_type, std::string>::value) - && (std::is_arithmetic::second_type>::value - || std::is_same::second_type, std::string>::value)); +struct IsDumpableType { + static constexpr bool value = std::is_trivially_copyable::value + || (PairTrait::value + && std::is_trivially_copyable::first_type>::value + && std::is_trivially_copyable::second_type>::value); }; template diff --git a/parallel_hashmap/phmap_utils.h b/parallel_hashmap/phmap_utils.h index 3807498..e517afd 100644 --- a/parallel_hashmap/phmap_utils.h +++ b/parallel_hashmap/phmap_utils.h @@ -351,29 +351,21 @@ public: } template - typename std::enable_if::value, bool>::type + typename std::enable_if::value, bool>::type dump(const V& v) { CHECK_FILE(ofs_); ofs_.write(reinterpret_cast(const_cast(&v)), sizeof(V)); return true; } - template - typename std::enable_if::type>::value, bool>::type - dump(const V& v) { - CHECK_FILE(ofs_); - uint32_t sz = v.length(); - ofs_.write(reinterpret_cast(&sz), sizeof(sz)); - ofs_.write(const_cast(v.data()), sz); - return true; - } - template typename std::enable_if::value - && type_traits_internal::IsStringOrArithmeticType::value, bool>::type + && type_traits_internal::IsDumpableType::value, bool>::type dump(const V& v) { - return dump::first_type>(v.first) - && dump::second_type>(v.second); + using first_type = typename type_traits_internal::PairTrait::first_type; + using second_type = typename type_traits_internal::PairTrait::second_type; + return dump(v.first) + && dump(v.second); } void finish() { @@ -405,32 +397,21 @@ public: } template - typename std::enable_if::value, bool>::type + typename std::enable_if::value, bool>::type load(V* v) { CHECK_FILE(ifs_); ifs_.read(reinterpret_cast(v), sizeof(V)); return true; } - template - typename std::enable_if::type>::value, bool>::type - load(V* v) { - CHECK_FILE(ifs_); - uint32_t sz = 0; - ifs_.read(reinterpret_cast(&sz), sizeof(sz)); - const_cast(v)->resize(sz); - ifs_.read(const_cast(v->data()), sz); - return true; - } - template typename std::enable_if::value - && type_traits_internal::IsStringOrArithmeticType::value, bool>::type + && type_traits_internal::IsDumpableType::value, bool>::type load(V* v) { - using first_type = typename type_traits_internal::PairTrait::first_type; - using second_type = typename type_traits_internal::PairTrait::second_type; - return load(const_cast(&v->first)) - && load(const_cast(&v->second)); + using first_type = typename std::remove_cv::first_type>::type; + using second_type = typename std::remove_cv::second_type>::type; + return load(const_cast(&v->first)) + && load(const_cast(&v->second)); } void finish() { diff --git a/tests/dump_load_test.cc b/tests/dump_load_test.cc index b4dc2fe..e162ba0 100644 --- a/tests/dump_load_test.cc +++ b/tests/dump_load_test.cc @@ -8,6 +8,7 @@ namespace phmap { namespace container_internal { namespace { + using ::phmap::flat_hash_set; using ::phmap::flat_hash_map; using ::phmap::parallel_flat_hash_map; @@ -22,7 +23,7 @@ TEST(DumpLoad, FlatHashSet_uin32) { st1.insert(1991); st1.insert(1202); - + EXPECT_TRUE(st1.dump(ar_out)); flat_hash_set st2; BinaryInputArchive ar_in("./dump.data"); @@ -81,3 +82,5 @@ TEST(DumpLoad, ParallelFlatHashMap_uint64_uint32) { } } +} +