abseil-cpp
abseil-cpp copied to clipboard
evaluate layout-compatible at compile time for flat hash map
In the current implementation, the key type of flat_hash_map must be copyable even we never copy it actually.
Because in the map_slot_policy, the layout compatibility of key & value pair will be evaluated at runtime, even its value is true (layout-compatible), the code in the false branch will be compiled. Then the key type must be copyable to avoid the compile error.
This PR will evaluate the layout compatibility in the compile time by template specializations. By this way, the type non-copyable but layout-compatible could be used as key of flat_hash_map.
Here is a snippet about this problem.
// Construct this slot by moving from another slot.
template <class Allocator>
static void construct(Allocator* alloc, slot_type* slot, slot_type* other) {
emplace(slot);
if (kMutableKeys::value) {
absl::allocator_traits<Allocator>::construct(
*alloc, &slot->mutable_value, std::move(other->mutable_value));
} else {
// --------- Copy semantic for key type is necessary here. --------
absl::allocator_traits<Allocator>::construct(*alloc, &slot->value,
std::move(other->value));
}
}
Free free to tell me and close this PR if it's not a problem but a special design. Thanks.
Hi, @derekmauro, thanks for the help to run the ci. Seems one of the ci build is failed. But how can I get the more detailed failure message then I can try to fix it?
get it. I will add a test for it.
a test case was added.
Please re-base this on head and run the tests. There is a new test in flat_hash_map_test.cc that doesn't build.
get it.
cc @derekmauro
The failure is introduced by this test case. We cannot evaluate layout-compatibility at compile time for this RecursiveType because it's incomplete type.
The latest commit solved this problem by handle these imcomplete types as special cases.
TEST(FlatHashMap, RecursiveTypeCompiles) {
struct RecursiveType {
flat_hash_map<int, RecursiveType> m;
};
RecursiveType t;
t.m[0] = RecursiveType{};
}
hmmm, one ci still failed. not sure if it's a flaky. 🤔
I tested this change on our codebase and unfortunately it causes over 2000 targets to no longer compile. Unfortunately I can't share the errors, and right now I don't have time to see if there is a reasonable fix. But I will leave this open if I get some time.
get it, thanks for all your helps. 🙏
Closing due to staleness and build failures.