implement EntityIndexMap/Set#17449
Conversation
|
As discussed on Discord, we should adopt #17447 to apply to the |
|
Note: this currently only includes slicing via deref. It'd put this PR well over a thousand lines to add the wrappers for those as well, so I'll do that as a follow-up. |
|
Actually, before I merge this, can you say a bit more on the motivation here? Adding code like this isn't free, and we don't have any internal users currently. |
Fair, I've added some more extensive motivation. |
…evyengine#17450) # Objective Noticed while doing bevyengine#17449, I had left these `DerefMut` impls in. Obtaining mutable references to those inner iterator types allows for `mem::swap`, which can be used to swap an incorrectly behaving instance into the wrappers. ## Solution Remove them!
# Objective We do not have `EntityIndexMap`/`EntityIndexSet`. Usual `HashMap`s/`HashSet`s do not guarantee any order, which can be awkward for some use cases. The `indexmap` versions remember insertion order, which then also becomes their iteration order. They can be thought of as a `HashTable` + `Vec`, which means fast iteration and removal, indexing by index (not just key), and slicing! Performance should otherwise be comparable. ## Solution Because `indexmap` is structured to mirror `hashbrown`, it suffers the same issue of not having the `Hasher` generic on their iterators. bevyengine#16912 solved this issue for `EntityHashMap`/`EntityHashSet` with a wrapper around the hashbrown version, so this PR does the same. Hopefully these wrappers can be removed again in the future by having `hashbrown`/`indexmap` adopt that generic in their iterators themselves!
# Objective Continuation of #17449. #17449 implemented the wrapper types around `IndexMap`/`Set` and co., however punted on the slice types. They are needed to support creating `EntitySetIterator`s from their slices, not just the base maps and sets. ## Solution Add the wrappers, in the same vein as #17449 and #17589 before. The `Index`/`IndexMut` implementations take up a lot of space, however they cannot be merged because we'd then get overlaps. They are simply named `Slice` to match the `indexmap` naming scheme, but this means they cannot be differentiated properly until their modules are made public, which is already a follow-up mentioned in #17954.
Objective
We do not have
EntityIndexMap/EntityIndexSet.Usual
HashMaps/HashSets do not guarantee any order, which can be awkward for some use cases.The
indexmapversions remember insertion order, which then also becomes their iteration order.They can be thought of as a
HashTable+Vec, which means fast iteration and removal, indexing by index (not just key), and slicing!Performance should otherwise be comparable.
Solution
Because
indexmapis structured to mirrorhashbrown, it suffers the same issue of not having theHashergeneric on their iterators. #16912 solved this issue forEntityHashMap/EntityHashSetwith a wrapper around the hashbrown version, so this PR does the same.Hopefully these wrappers can be removed again in the future by having
hashbrown/indexmapadopt that generic in their iterators themselves!