diff options
author | Jacques Lucke <jacques@blender.org> | 2020-10-12 16:10:01 +0300 |
---|---|---|
committer | Jacques Lucke <jacques@blender.org> | 2020-10-12 16:10:08 +0300 |
commit | db8a856a747042b6a544f4dc778219dcaaf6540f (patch) | |
tree | 48bf4fbb241db95496c5bb418a909e19ca1f4735 /source/blender/blenlib/BLI_set.hh | |
parent | 662c0ac970b3fe9fd63105f9ff1f2bb2553378f4 (diff) |
BLI: support looking up a key from a set or adding it when not existant
Diffstat (limited to 'source/blender/blenlib/BLI_set.hh')
-rw-r--r-- | source/blender/blenlib/BLI_set.hh | 33 |
1 files changed, 33 insertions, 0 deletions
diff --git a/source/blender/blenlib/BLI_set.hh b/source/blender/blenlib/BLI_set.hh index 9684f372db7..f1cf44018c9 100644 --- a/source/blender/blenlib/BLI_set.hh +++ b/source/blender/blenlib/BLI_set.hh @@ -351,6 +351,23 @@ class Set { } /** + * Returns the key in the set that compares equal to the given key. If it does not exist, the key + * is newly added. + */ + const Key &lookup_key_or_add(const Key &key) + { + return this->lookup_key_or_add_as(key); + } + const Key &lookup_key_or_add(Key &&key) + { + return this->lookup_key_or_add_as(std::move(key)); + } + template<typename ForwardKey> const Key &lookup_key_or_add_as(ForwardKey &&key) + { + return this->lookup_key_or_add__impl(std::forward<ForwardKey>(key), hash_(key)); + } + + /** * Deletes the key from the set. Returns true when the key did exist beforehand, otherwise false. * * This is similar to std::unordered_set::erase. @@ -735,6 +752,22 @@ class Set { } template<typename ForwardKey> + const Key &lookup_key_or_add__impl(ForwardKey &&key, const uint64_t hash) + { + SET_SLOT_PROBING_BEGIN (hash, slot) { + if (slot.contains(key, is_equal_, hash)) { + return *slot.key(); + } + if (slot.is_empty()) { + slot.occupy(std::forward<ForwardKey>(key), hash); + occupied_and_removed_slots_++; + return *slot.key(); + } + } + SET_SLOT_PROBING_END(); + } + + template<typename ForwardKey> int64_t count_collisions__impl(const ForwardKey &key, const uint64_t hash) const { int64_t collisions = 0; |