Path: blob/main/crates/bevy_platform/src/collections/hash_map.rs
9334 views
//! Provides [`HashMap`] based on [hashbrown]'s implementation.1//! Unlike [`hashbrown::HashMap`], [`HashMap`] defaults to [`FixedHasher`]2//! instead of [`RandomState`].3//! This provides determinism by default with an acceptable compromise to denial4//! of service resistance in the context of a game engine.56use core::{7fmt::Debug,8hash::{BuildHasher, Hash},9ops::{Deref, DerefMut, Index},10};1112use hashbrown::{hash_map as hb, Equivalent};1314use crate::hash::FixedHasher;1516#[cfg(feature = "rayon")]17use rayon::prelude::{FromParallelIterator, IntoParallelIterator, ParallelExtend};1819// Re-exports to match `std::collections::hash_map`20pub use {21crate::hash::{DefaultHasher, RandomState},22hb::{23Drain, IntoIter, IntoKeys, IntoValues, Iter, IterMut, Keys, OccupiedEntry, VacantEntry,24Values, ValuesMut,25},26};2728// Additional items from `hashbrown`29pub use hb::{30EntryRef, ExtractIf, OccupiedError, RawEntryBuilder, RawEntryBuilderMut, RawEntryMut,31RawOccupiedEntryMut,32};3334/// Shortcut for [`Entry`](hb::Entry) with [`FixedHasher`] as the default hashing provider.35pub type Entry<'a, K, V, S = FixedHasher> = hb::Entry<'a, K, V, S>;3637/// New-type for [`HashMap`](hb::HashMap) with [`FixedHasher`] as the default hashing provider.38/// Can be trivially converted to and from a [hashbrown] [`HashMap`](hb::HashMap) using [`From`].39///40/// A new-type is used instead of a type alias due to critical methods like [`new`](hb::HashMap::new)41/// being incompatible with Bevy's choice of default hasher.42///43/// Unlike [`hashbrown::HashMap`], [`HashMap`] defaults to [`FixedHasher`]44/// instead of [`RandomState`].45/// This provides determinism by default with an acceptable compromise to denial46/// of service resistance in the context of a game engine.47#[repr(transparent)]48pub struct HashMap<K, V, S = FixedHasher>(hb::HashMap<K, V, S>);4950impl<K, V, S> Clone for HashMap<K, V, S>51where52hb::HashMap<K, V, S>: Clone,53{54#[inline]55fn clone(&self) -> Self {56Self(self.0.clone())57}5859#[inline]60fn clone_from(&mut self, source: &Self) {61self.0.clone_from(&source.0);62}63}6465impl<K, V, S> Debug for HashMap<K, V, S>66where67hb::HashMap<K, V, S>: Debug,68{69#[inline]70fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {71<hb::HashMap<K, V, S> as Debug>::fmt(&self.0, f)72}73}7475impl<K, V, S> Default for HashMap<K, V, S>76where77hb::HashMap<K, V, S>: Default,78{79#[inline]80fn default() -> Self {81Self(Default::default())82}83}8485impl<K, V, S> PartialEq for HashMap<K, V, S>86where87hb::HashMap<K, V, S>: PartialEq,88{89#[inline]90fn eq(&self, other: &Self) -> bool {91self.0.eq(&other.0)92}93}9495impl<K, V, S> Eq for HashMap<K, V, S> where hb::HashMap<K, V, S>: Eq {}9697impl<K, V, S, T> FromIterator<T> for HashMap<K, V, S>98where99hb::HashMap<K, V, S>: FromIterator<T>,100{101#[inline]102fn from_iter<U: IntoIterator<Item = T>>(iter: U) -> Self {103Self(FromIterator::from_iter(iter))104}105}106107impl<K, V, S, T> Index<T> for HashMap<K, V, S>108where109hb::HashMap<K, V, S>: Index<T>,110{111type Output = <hb::HashMap<K, V, S> as Index<T>>::Output;112113#[inline]114fn index(&self, index: T) -> &Self::Output {115self.0.index(index)116}117}118119impl<K, V, S> IntoIterator for HashMap<K, V, S>120where121hb::HashMap<K, V, S>: IntoIterator,122{123type Item = <hb::HashMap<K, V, S> as IntoIterator>::Item;124125type IntoIter = <hb::HashMap<K, V, S> as IntoIterator>::IntoIter;126127#[inline]128fn into_iter(self) -> Self::IntoIter {129self.0.into_iter()130}131}132133impl<'a, K, V, S> IntoIterator for &'a HashMap<K, V, S>134where135&'a hb::HashMap<K, V, S>: IntoIterator,136{137type Item = <&'a hb::HashMap<K, V, S> as IntoIterator>::Item;138139type IntoIter = <&'a hb::HashMap<K, V, S> as IntoIterator>::IntoIter;140141#[inline]142fn into_iter(self) -> Self::IntoIter {143(&self.0).into_iter()144}145}146147impl<'a, K, V, S> IntoIterator for &'a mut HashMap<K, V, S>148where149&'a mut hb::HashMap<K, V, S>: IntoIterator,150{151type Item = <&'a mut hb::HashMap<K, V, S> as IntoIterator>::Item;152153type IntoIter = <&'a mut hb::HashMap<K, V, S> as IntoIterator>::IntoIter;154155#[inline]156fn into_iter(self) -> Self::IntoIter {157(&mut self.0).into_iter()158}159}160161impl<K, V, S, T> Extend<T> for HashMap<K, V, S>162where163hb::HashMap<K, V, S>: Extend<T>,164{165#[inline]166fn extend<U: IntoIterator<Item = T>>(&mut self, iter: U) {167self.0.extend(iter);168}169}170171impl<K, V, const N: usize> From<[(K, V); N]> for HashMap<K, V, FixedHasher>172where173K: Eq + Hash,174{175fn from(arr: [(K, V); N]) -> Self {176arr.into_iter().collect()177}178}179180impl<K, V, S> From<hb::HashMap<K, V, S>> for HashMap<K, V, S> {181#[inline]182fn from(value: hb::HashMap<K, V, S>) -> Self {183Self(value)184}185}186187impl<K, V, S> From<HashMap<K, V, S>> for hb::HashMap<K, V, S> {188#[inline]189fn from(value: HashMap<K, V, S>) -> Self {190value.0191}192}193194impl<K, V, S> Deref for HashMap<K, V, S> {195type Target = hb::HashMap<K, V, S>;196197#[inline]198fn deref(&self) -> &Self::Target {199&self.0200}201}202203impl<K, V, S> DerefMut for HashMap<K, V, S> {204#[inline]205fn deref_mut(&mut self) -> &mut Self::Target {206&mut self.0207}208}209210#[cfg(feature = "serialize")]211impl<K, V, S> serde::Serialize for HashMap<K, V, S>212where213hb::HashMap<K, V, S>: serde::Serialize,214{215#[inline]216fn serialize<T>(&self, serializer: T) -> Result<T::Ok, T::Error>217where218T: serde::Serializer,219{220self.0.serialize(serializer)221}222}223224#[cfg(feature = "serialize")]225impl<'de, K, V, S> serde::Deserialize<'de> for HashMap<K, V, S>226where227hb::HashMap<K, V, S>: serde::Deserialize<'de>,228{229#[inline]230fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>231where232D: serde::Deserializer<'de>,233{234Ok(Self(serde::Deserialize::deserialize(deserializer)?))235}236}237238#[cfg(feature = "rayon")]239impl<K, V, S, T> FromParallelIterator<T> for HashMap<K, V, S>240where241hb::HashMap<K, V, S>: FromParallelIterator<T>,242T: Send,243{244fn from_par_iter<P>(par_iter: P) -> Self245where246P: IntoParallelIterator<Item = T>,247{248Self(<hb::HashMap<K, V, S> as FromParallelIterator<T>>::from_par_iter(par_iter))249}250}251252#[cfg(feature = "rayon")]253impl<K, V, S> IntoParallelIterator for HashMap<K, V, S>254where255hb::HashMap<K, V, S>: IntoParallelIterator,256{257type Item = <hb::HashMap<K, V, S> as IntoParallelIterator>::Item;258type Iter = <hb::HashMap<K, V, S> as IntoParallelIterator>::Iter;259260fn into_par_iter(self) -> Self::Iter {261self.0.into_par_iter()262}263}264265#[cfg(feature = "rayon")]266impl<'a, K: Sync, V: Sync, S> IntoParallelIterator for &'a HashMap<K, V, S>267where268&'a hb::HashMap<K, V, S>: IntoParallelIterator,269{270type Item = <&'a hb::HashMap<K, V, S> as IntoParallelIterator>::Item;271type Iter = <&'a hb::HashMap<K, V, S> as IntoParallelIterator>::Iter;272273fn into_par_iter(self) -> Self::Iter {274(&self.0).into_par_iter()275}276}277278#[cfg(feature = "rayon")]279impl<'a, K: Sync, V: Sync, S> IntoParallelIterator for &'a mut HashMap<K, V, S>280where281&'a mut hb::HashMap<K, V, S>: IntoParallelIterator,282{283type Item = <&'a mut hb::HashMap<K, V, S> as IntoParallelIterator>::Item;284type Iter = <&'a mut hb::HashMap<K, V, S> as IntoParallelIterator>::Iter;285286fn into_par_iter(self) -> Self::Iter {287(&mut self.0).into_par_iter()288}289}290291#[cfg(feature = "rayon")]292impl<K, V, S, T> ParallelExtend<T> for HashMap<K, V, S>293where294hb::HashMap<K, V, S>: ParallelExtend<T>,295T: Send,296{297fn par_extend<I>(&mut self, par_iter: I)298where299I: IntoParallelIterator<Item = T>,300{301<hb::HashMap<K, V, S> as ParallelExtend<T>>::par_extend(&mut self.0, par_iter);302}303}304305impl<K, V> HashMap<K, V, FixedHasher> {306/// Creates an empty [`HashMap`].307///308/// Refer to [`new`](hb::HashMap::new) for further details.309///310/// # Examples311///312/// ```rust313/// # use bevy_platform::collections::HashMap;314/// #315/// // Creates a HashMap with zero capacity.316/// let map = HashMap::new();317/// #318/// # let mut map = map;319/// # map.insert(0usize, "foo");320/// # assert_eq!(map.get(&0), Some("foo").as_ref());321/// ```322#[inline]323pub const fn new() -> Self {324Self::with_hasher(FixedHasher)325}326327/// Creates an empty [`HashMap`] with the specified capacity.328///329/// Refer to [`with_capacity`](hb::HashMap::with_capacity) for further details.330///331/// # Examples332///333/// ```rust334/// # use bevy_platform::collections::HashMap;335/// #336/// // Creates a HashMap with capacity for at least 5 entries.337/// let map = HashMap::with_capacity(5);338/// #339/// # let mut map = map;340/// # map.insert(0usize, "foo");341/// # assert_eq!(map.get(&0), Some("foo").as_ref());342/// ```343#[inline]344pub fn with_capacity(capacity: usize) -> Self {345Self::with_capacity_and_hasher(capacity, FixedHasher)346}347}348349impl<K, V, S> HashMap<K, V, S> {350/// Creates an empty [`HashMap`] which will use the given hash builder to hash351/// keys.352///353/// Refer to [`with_hasher`](hb::HashMap::with_hasher) for further details.354///355/// # Examples356///357/// ```rust358/// # use bevy_platform::collections::HashMap;359/// # use bevy_platform::hash::FixedHasher as SomeHasher;360/// // Creates a HashMap with the provided hasher.361/// let map = HashMap::with_hasher(SomeHasher);362/// #363/// # let mut map = map;364/// # map.insert(0usize, "foo");365/// # assert_eq!(map.get(&0), Some("foo").as_ref());366/// ```367#[inline]368pub const fn with_hasher(hash_builder: S) -> Self {369Self(hb::HashMap::with_hasher(hash_builder))370}371372/// Creates an empty [`HashMap`] with the specified capacity, using `hash_builder`373/// to hash the keys.374///375/// Refer to [`with_capacity_and_hasher`](hb::HashMap::with_capacity_and_hasher) for further details.376///377/// # Examples378///379/// ```rust380/// # use bevy_platform::collections::HashMap;381/// # use bevy_platform::hash::FixedHasher as SomeHasher;382/// // Creates a HashMap with capacity for 5 entries and the provided hasher.383/// let map = HashMap::with_capacity_and_hasher(5, SomeHasher);384/// #385/// # let mut map = map;386/// # map.insert(0usize, "foo");387/// # assert_eq!(map.get(&0), Some("foo").as_ref());388/// ```389#[inline]390pub fn with_capacity_and_hasher(capacity: usize, hash_builder: S) -> Self {391Self(hb::HashMap::with_capacity_and_hasher(392capacity,393hash_builder,394))395}396397/// Returns a reference to the map's [`BuildHasher`], or `S` parameter.398///399/// Refer to [`hasher`](hb::HashMap::hasher) for further details.400#[inline]401pub fn hasher(&self) -> &S {402self.0.hasher()403}404405/// Returns the number of elements the map can hold without reallocating.406///407/// Refer to [`capacity`](hb::HashMap::capacity) for further details.408///409/// # Examples410///411/// ```rust412/// # use bevy_platform::collections::HashMap;413/// let map = HashMap::with_capacity(5);414///415/// # let map: HashMap<(), ()> = map;416/// #417/// assert!(map.capacity() >= 5);418/// ```419#[inline]420pub fn capacity(&self) -> usize {421self.0.capacity()422}423424/// An iterator visiting all keys in arbitrary order.425/// The iterator element type is `&'a K`.426///427/// Refer to [`keys`](hb::HashMap::keys) for further details.428///429/// # Examples430///431/// ```rust432/// # use bevy_platform::collections::HashMap;433/// #434/// let mut map = HashMap::new();435///436/// map.insert("foo", 0);437/// map.insert("bar", 1);438/// map.insert("baz", 2);439///440/// for key in map.keys() {441/// // foo, bar, baz442/// // Note that the above order is not guaranteed443/// }444/// #445/// # assert_eq!(map.keys().count(), 3);446/// ```447#[inline]448pub fn keys(&self) -> Keys<'_, K, V> {449self.0.keys()450}451452/// An iterator visiting all values in arbitrary order.453/// The iterator element type is `&'a V`.454///455/// Refer to [`values`](hb::HashMap::values) for further details.456///457/// # Examples458///459/// ```rust460/// # use bevy_platform::collections::HashMap;461/// #462/// let mut map = HashMap::new();463///464/// map.insert("foo", 0);465/// map.insert("bar", 1);466/// map.insert("baz", 2);467///468/// for key in map.values() {469/// // 0, 1, 2470/// // Note that the above order is not guaranteed471/// }472/// #473/// # assert_eq!(map.values().count(), 3);474/// ```475#[inline]476pub fn values(&self) -> Values<'_, K, V> {477self.0.values()478}479480/// An iterator visiting all values mutably in arbitrary order.481/// The iterator element type is `&'a mut V`.482///483/// Refer to [`values`](hb::HashMap::values) for further details.484///485/// # Examples486///487/// ```rust488/// # use bevy_platform::collections::HashMap;489/// #490/// let mut map = HashMap::new();491///492/// map.insert("foo", 0);493/// map.insert("bar", 1);494/// map.insert("baz", 2);495///496/// for key in map.values_mut() {497/// // 0, 1, 2498/// // Note that the above order is not guaranteed499/// }500/// #501/// # assert_eq!(map.values_mut().count(), 3);502/// ```503#[inline]504pub fn values_mut(&mut self) -> ValuesMut<'_, K, V> {505self.0.values_mut()506}507508/// An iterator visiting all key-value pairs in arbitrary order.509/// The iterator element type is `(&'a K, &'a V)`.510///511/// Refer to [`iter`](hb::HashMap::iter) for further details.512///513/// # Examples514///515/// ```rust516/// # use bevy_platform::collections::HashMap;517/// #518/// let mut map = HashMap::new();519///520/// map.insert("foo", 0);521/// map.insert("bar", 1);522/// map.insert("baz", 2);523///524/// for (key, value) in map.iter() {525/// // ("foo", 0), ("bar", 1), ("baz", 2)526/// // Note that the above order is not guaranteed527/// }528/// #529/// # assert_eq!(map.iter().count(), 3);530/// ```531#[inline]532pub fn iter(&self) -> Iter<'_, K, V> {533self.0.iter()534}535536/// An iterator visiting all key-value pairs in arbitrary order,537/// with mutable references to the values.538/// The iterator element type is `(&'a K, &'a mut V)`.539///540/// Refer to [`iter_mut`](hb::HashMap::iter_mut) for further details.541///542/// # Examples543///544/// ```rust545/// # use bevy_platform::collections::HashMap;546/// #547/// let mut map = HashMap::new();548///549/// map.insert("foo", 0);550/// map.insert("bar", 1);551/// map.insert("baz", 2);552///553/// for (key, value) in map.iter_mut() {554/// // ("foo", 0), ("bar", 1), ("baz", 2)555/// // Note that the above order is not guaranteed556/// }557/// #558/// # assert_eq!(map.iter_mut().count(), 3);559/// ```560#[inline]561pub fn iter_mut(&mut self) -> IterMut<'_, K, V> {562self.0.iter_mut()563}564565/// Returns the number of elements in the map.566///567/// Refer to [`len`](hb::HashMap::len) for further details.568///569/// # Examples570///571/// ```rust572/// # use bevy_platform::collections::HashMap;573/// let mut map = HashMap::new();574///575/// assert_eq!(map.len(), 0);576///577/// map.insert("foo", 0);578///579/// assert_eq!(map.len(), 1);580/// ```581#[inline]582pub fn len(&self) -> usize {583self.0.len()584}585586/// Returns `true` if the map contains no elements.587///588/// Refer to [`is_empty`](hb::HashMap::is_empty) for further details.589///590/// # Examples591///592/// ```rust593/// # use bevy_platform::collections::HashMap;594/// let mut map = HashMap::new();595///596/// assert!(map.is_empty());597///598/// map.insert("foo", 0);599///600/// assert!(!map.is_empty());601/// ```602#[inline]603pub fn is_empty(&self) -> bool {604self.0.is_empty()605}606607/// Clears the map, returning all key-value pairs as an iterator. Keeps the608/// allocated memory for reuse.609///610/// Refer to [`drain`](hb::HashMap::drain) for further details.611///612/// # Examples613///614/// ```rust615/// # use bevy_platform::collections::HashMap;616/// #617/// let mut map = HashMap::new();618///619/// map.insert("foo", 0);620/// map.insert("bar", 1);621/// map.insert("baz", 2);622///623/// for (key, value) in map.drain() {624/// // ("foo", 0), ("bar", 1), ("baz", 2)625/// // Note that the above order is not guaranteed626/// }627///628/// assert!(map.is_empty());629/// ```630#[inline]631pub fn drain(&mut self) -> Drain<'_, K, V> {632self.0.drain()633}634635/// Retains only the elements specified by the predicate. Keeps the636/// allocated memory for reuse.637///638/// Refer to [`retain`](hb::HashMap::retain) for further details.639///640/// # Examples641///642/// ```rust643/// # use bevy_platform::collections::HashMap;644/// #645/// let mut map = HashMap::new();646///647/// map.insert("foo", 0);648/// map.insert("bar", 1);649/// map.insert("baz", 2);650///651/// map.retain(|key, value| *value == 2);652///653/// assert_eq!(map.len(), 1);654/// ```655#[inline]656pub fn retain<F>(&mut self, f: F)657where658F: FnMut(&K, &mut V) -> bool,659{660self.0.retain(f);661}662663/// Drains elements which are true under the given predicate,664/// and returns an iterator over the removed items.665///666/// Refer to [`extract_if`](hb::HashMap::extract_if) for further details.667///668/// # Examples669///670/// ```rust671/// # use bevy_platform::collections::HashMap;672/// #673/// let mut map = HashMap::new();674///675/// map.insert("foo", 0);676/// map.insert("bar", 1);677/// map.insert("baz", 2);678///679/// let extracted = map680/// .extract_if(|key, value| *value == 2)681/// .collect::<Vec<_>>();682///683/// assert_eq!(map.len(), 2);684/// assert_eq!(extracted.len(), 1);685/// ```686#[inline]687pub fn extract_if<F>(&mut self, f: F) -> ExtractIf<'_, K, V, F>688where689F: FnMut(&K, &mut V) -> bool,690{691self.0.extract_if(f)692}693694/// Clears the map, removing all key-value pairs. Keeps the allocated memory695/// for reuse.696///697/// Refer to [`clear`](hb::HashMap::clear) for further details.698///699/// # Examples700///701/// ```rust702/// # use bevy_platform::collections::HashMap;703/// #704/// let mut map = HashMap::new();705///706/// map.insert("foo", 0);707/// map.insert("bar", 1);708/// map.insert("baz", 2);709///710/// map.clear();711///712/// assert!(map.is_empty());713/// ```714#[inline]715pub fn clear(&mut self) {716self.0.clear();717}718719/// Creates a consuming iterator visiting all the keys in arbitrary order.720/// The map cannot be used after calling this.721/// The iterator element type is `K`.722///723/// Refer to [`into_keys`](hb::HashMap::into_keys) for further details.724///725/// # Examples726///727/// ```rust728/// # use bevy_platform::collections::HashMap;729/// #730/// let mut map = HashMap::new();731///732/// map.insert("foo", 0);733/// map.insert("bar", 1);734/// map.insert("baz", 2);735///736/// for key in map.into_keys() {737/// // "foo", "bar", "baz"738/// // Note that the above order is not guaranteed739/// }740/// ```741#[inline]742pub fn into_keys(self) -> IntoKeys<K, V> {743self.0.into_keys()744}745746/// Creates a consuming iterator visiting all the values in arbitrary order.747/// The map cannot be used after calling this.748/// The iterator element type is `V`.749///750/// Refer to [`into_values`](hb::HashMap::into_values) for further details.751///752/// # Examples753///754/// ```rust755/// # use bevy_platform::collections::HashMap;756/// #757/// let mut map = HashMap::new();758///759/// map.insert("foo", 0);760/// map.insert("bar", 1);761/// map.insert("baz", 2);762///763/// for key in map.into_values() {764/// // 0, 1, 2765/// // Note that the above order is not guaranteed766/// }767/// ```768#[inline]769pub fn into_values(self) -> IntoValues<K, V> {770self.0.into_values()771}772773/// Takes the inner [`HashMap`](hb::HashMap) out of this wrapper.774///775/// # Examples776///777/// ```rust778/// # use bevy_platform::collections::HashMap;779/// let map: HashMap<&'static str, usize> = HashMap::new();780/// let map: hashbrown::HashMap<&'static str, usize, _> = map.into_inner();781/// ```782#[inline]783pub fn into_inner(self) -> hb::HashMap<K, V, S> {784self.0785}786}787788impl<K, V, S> HashMap<K, V, S>789where790K: Eq + Hash,791S: BuildHasher,792{793/// Reserves capacity for at least `additional` more elements to be inserted794/// in the [`HashMap`]. The collection may reserve more space to avoid795/// frequent reallocations.796///797/// Refer to [`reserve`](hb::HashMap::reserve) for further details.798///799/// # Examples800///801/// ```rust802/// # use bevy_platform::collections::HashMap;803/// let mut map = HashMap::with_capacity(5);804///805/// # let mut map: HashMap<(), ()> = map;806/// #807/// assert!(map.capacity() >= 5);808///809/// map.reserve(10);810///811/// assert!(map.capacity() - map.len() >= 10);812/// ```813#[inline]814pub fn reserve(&mut self, additional: usize) {815self.0.reserve(additional);816}817818/// Tries to reserve capacity for at least `additional` more elements to be inserted819/// in the given `HashMap<K,V>`. The collection may reserve more space to avoid820/// frequent reallocations.821///822/// Refer to [`try_reserve`](hb::HashMap::try_reserve) for further details.823///824/// # Examples825///826/// ```rust827/// # use bevy_platform::collections::HashMap;828/// let mut map = HashMap::with_capacity(5);829///830/// # let mut map: HashMap<(), ()> = map;831/// #832/// assert!(map.capacity() >= 5);833///834/// map.try_reserve(10).expect("Out of Memory!");835///836/// assert!(map.capacity() - map.len() >= 10);837/// ```838#[inline]839pub fn try_reserve(&mut self, additional: usize) -> Result<(), hashbrown::TryReserveError> {840self.0.try_reserve(additional)841}842843/// Shrinks the capacity of the map as much as possible. It will drop844/// down as much as possible while maintaining the internal rules845/// and possibly leaving some space in accordance with the resize policy.846///847/// Refer to [`shrink_to_fit`](hb::HashMap::shrink_to_fit) for further details.848///849/// # Examples850///851/// ```rust852/// # use bevy_platform::collections::HashMap;853/// let mut map = HashMap::with_capacity(5);854///855/// map.insert("foo", 0);856/// map.insert("bar", 1);857/// map.insert("baz", 2);858///859/// assert!(map.capacity() >= 5);860///861/// map.shrink_to_fit();862///863/// assert_eq!(map.capacity(), 3);864/// ```865#[inline]866pub fn shrink_to_fit(&mut self) {867self.0.shrink_to_fit();868}869870/// Shrinks the capacity of the map with a lower limit. It will drop871/// down no lower than the supplied limit while maintaining the internal rules872/// and possibly leaving some space in accordance with the resize policy.873///874/// Refer to [`shrink_to`](hb::HashMap::shrink_to) for further details.875#[inline]876pub fn shrink_to(&mut self, min_capacity: usize) {877self.0.shrink_to(min_capacity);878}879880/// Gets the given key's corresponding entry in the map for in-place manipulation.881///882/// Refer to [`entry`](hb::HashMap::entry) for further details.883///884/// # Examples885///886/// ```rust887/// # use bevy_platform::collections::HashMap;888/// let mut map = HashMap::new();889///890/// let value = map.entry("foo").or_insert(0);891/// #892/// # assert_eq!(*value, 0);893/// ```894#[inline]895pub fn entry(&mut self, key: K) -> Entry<'_, K, V, S> {896self.0.entry(key)897}898899/// Gets the given key's corresponding entry by reference in the map for in-place manipulation.900///901/// Refer to [`entry_ref`](hb::HashMap::entry_ref) for further details.902///903/// # Examples904///905/// ```rust906/// # use bevy_platform::collections::HashMap;907/// let mut map = HashMap::new();908/// # let mut map: HashMap<&'static str, usize> = map;909///910/// let value = map.entry_ref("foo").or_insert(0);911/// #912/// # assert_eq!(*value, 0);913/// ```914#[inline]915pub fn entry_ref<'a, 'b, Q>(&'a mut self, key: &'b Q) -> EntryRef<'a, 'b, K, Q, V, S>916where917Q: Hash + Equivalent<K> + ?Sized,918{919self.0.entry_ref(key)920}921922/// Returns a reference to the value corresponding to the key.923///924/// Refer to [`get`](hb::HashMap::get) for further details.925///926/// # Examples927///928/// ```rust929/// # use bevy_platform::collections::HashMap;930/// let mut map = HashMap::new();931///932/// map.insert("foo", 0);933///934/// assert_eq!(map.get("foo"), Some(&0));935/// ```936#[inline]937pub fn get<Q>(&self, k: &Q) -> Option<&V>938where939Q: Hash + Equivalent<K> + ?Sized,940{941self.0.get(k)942}943944/// Returns the key-value pair corresponding to the supplied key.945///946/// Refer to [`get_key_value`](hb::HashMap::get_key_value) for further details.947///948/// # Examples949///950/// ```rust951/// # use bevy_platform::collections::HashMap;952/// let mut map = HashMap::new();953///954/// map.insert("foo", 0);955///956/// assert_eq!(map.get_key_value("foo"), Some((&"foo", &0)));957/// ```958#[inline]959pub fn get_key_value<Q>(&self, k: &Q) -> Option<(&K, &V)>960where961Q: Hash + Equivalent<K> + ?Sized,962{963self.0.get_key_value(k)964}965966/// Returns the key-value pair corresponding to the supplied key, with a mutable reference to value.967///968/// Refer to [`get_key_value_mut`](hb::HashMap::get_key_value_mut) for further details.969///970/// # Examples971///972/// ```rust973/// # use bevy_platform::collections::HashMap;974/// let mut map = HashMap::new();975///976/// map.insert("foo", 0);977///978/// assert_eq!(map.get_key_value_mut("foo"), Some((&"foo", &mut 0)));979/// ```980#[inline]981pub fn get_key_value_mut<Q>(&mut self, k: &Q) -> Option<(&K, &mut V)>982where983Q: Hash + Equivalent<K> + ?Sized,984{985self.0.get_key_value_mut(k)986}987988/// Returns `true` if the map contains a value for the specified key.989///990/// Refer to [`contains_key`](hb::HashMap::contains_key) for further details.991///992/// # Examples993///994/// ```rust995/// # use bevy_platform::collections::HashMap;996/// let mut map = HashMap::new();997///998/// map.insert("foo", 0);999///1000/// assert!(map.contains_key("foo"));1001/// ```1002#[inline]1003pub fn contains_key<Q>(&self, k: &Q) -> bool1004where1005Q: Hash + Equivalent<K> + ?Sized,1006{1007self.0.contains_key(k)1008}10091010/// Returns a mutable reference to the value corresponding to the key.1011///1012/// Refer to [`get_mut`](hb::HashMap::get_mut) for further details.1013///1014/// # Examples1015///1016/// ```rust1017/// # use bevy_platform::collections::HashMap;1018/// let mut map = HashMap::new();1019///1020/// map.insert("foo", 0);1021///1022/// assert_eq!(map.get_mut("foo"), Some(&mut 0));1023/// ```1024#[inline]1025pub fn get_mut<Q>(&mut self, k: &Q) -> Option<&mut V>1026where1027Q: Hash + Equivalent<K> + ?Sized,1028{1029self.0.get_mut(k)1030}10311032/// Attempts to get mutable references to `N` values in the map at once.1033///1034/// Refer to [`get_disjoint_mut`](hb::HashMap::get_disjoint_mut) for further details.1035///1036/// # Examples1037///1038/// ```rust1039/// # use bevy_platform::collections::HashMap;1040/// let mut map = HashMap::new();1041///1042/// map.insert("foo", 0);1043/// map.insert("bar", 1);1044/// map.insert("baz", 2);1045///1046/// let result = map.get_disjoint_mut(["foo", "bar"]);1047///1048/// assert_eq!(result, [Some(&mut 0), Some(&mut 1)]);1049/// ```1050#[inline]1051pub fn get_disjoint_mut<Q, const N: usize>(&mut self, ks: [&Q; N]) -> [Option<&'_ mut V>; N]1052where1053Q: Hash + Equivalent<K> + ?Sized,1054{1055self.0.get_disjoint_mut(ks)1056}10571058/// Attempts to get mutable references to `N` values in the map at once, with immutable1059/// references to the corresponding keys.1060///1061/// Refer to [`get_disjoint_key_value_mut`](hb::HashMap::get_disjoint_key_value_mut) for further details.1062///1063/// # Examples1064///1065/// ```rust1066/// # use bevy_platform::collections::HashMap;1067/// let mut map = HashMap::new();1068///1069/// map.insert("foo", 0);1070/// map.insert("bar", 1);1071/// map.insert("baz", 2);1072///1073/// let result = map.get_disjoint_key_value_mut(["foo", "bar"]);1074///1075/// assert_eq!(result, [Some((&"foo", &mut 0)), Some((&"bar", &mut 1))]);1076/// ```1077#[inline]1078pub fn get_disjoint_key_value_mut<Q, const N: usize>(1079&mut self,1080ks: [&Q; N],1081) -> [Option<(&'_ K, &'_ mut V)>; N]1082where1083Q: Hash + Equivalent<K> + ?Sized,1084{1085self.0.get_disjoint_key_value_mut(ks)1086}10871088/// Inserts a key-value pair into the map.1089///1090/// Refer to [`insert`](hb::HashMap::insert) for further details.1091///1092/// # Examples1093///1094/// ```rust1095/// # use bevy_platform::collections::HashMap;1096/// let mut map = HashMap::new();1097///1098/// map.insert("foo", 0);1099///1100/// assert_eq!(map.get("foo"), Some(&0));1101/// ```1102#[inline]1103pub fn insert(&mut self, k: K, v: V) -> Option<V> {1104self.0.insert(k, v)1105}11061107/// Tries to insert a key-value pair into the map, and returns1108/// a mutable reference to the value in the entry.1109///1110/// Refer to [`try_insert`](hb::HashMap::try_insert) for further details.1111///1112/// # Examples1113///1114/// ```rust1115/// # use bevy_platform::collections::HashMap;1116/// let mut map = HashMap::new();1117///1118/// map.try_insert("foo", 0).unwrap();1119///1120/// assert!(map.try_insert("foo", 1).is_err());1121/// ```1122#[inline]1123pub fn try_insert(&mut self, key: K, value: V) -> Result<&mut V, OccupiedError<'_, K, V, S>> {1124self.0.try_insert(key, value)1125}11261127/// Removes a key from the map, returning the value at the key if the key1128/// was previously in the map. Keeps the allocated memory for reuse.1129///1130/// Refer to [`remove`](hb::HashMap::remove) for further details.1131///1132/// # Examples1133///1134/// ```rust1135/// # use bevy_platform::collections::HashMap;1136/// let mut map = HashMap::new();1137///1138/// map.insert("foo", 0);1139///1140/// assert_eq!(map.remove("foo"), Some(0));1141///1142/// assert!(map.is_empty());1143/// ```1144#[inline]1145pub fn remove<Q>(&mut self, k: &Q) -> Option<V>1146where1147Q: Hash + Equivalent<K> + ?Sized,1148{1149self.0.remove(k)1150}11511152/// Removes a key from the map, returning the stored key and value if the1153/// key was previously in the map. Keeps the allocated memory for reuse.1154///1155/// Refer to [`remove_entry`](hb::HashMap::remove_entry) for further details.1156///1157/// # Examples1158///1159/// ```rust1160/// # use bevy_platform::collections::HashMap;1161/// let mut map = HashMap::new();1162///1163/// map.insert("foo", 0);1164///1165/// assert_eq!(map.remove_entry("foo"), Some(("foo", 0)));1166///1167/// assert!(map.is_empty());1168/// ```1169#[inline]1170pub fn remove_entry<Q>(&mut self, k: &Q) -> Option<(K, V)>1171where1172Q: Hash + Equivalent<K> + ?Sized,1173{1174self.0.remove_entry(k)1175}11761177/// Returns the total amount of memory allocated internally by the hash1178/// set, in bytes.1179///1180/// Refer to [`allocation_size`](hb::HashMap::allocation_size) for further details.1181///1182/// # Examples1183///1184/// ```rust1185/// # use bevy_platform::collections::HashMap;1186/// let mut map = HashMap::new();1187///1188/// assert_eq!(map.allocation_size(), 0);1189///1190/// map.insert("foo", 0u32);1191///1192/// assert!(map.allocation_size() >= size_of::<&'static str>() + size_of::<u32>());1193/// ```1194#[inline]1195pub fn allocation_size(&self) -> usize {1196self.0.allocation_size()1197}11981199/// Insert a key-value pair into the map without checking1200/// if the key already exists in the map.1201///1202/// Refer to [`insert_unique_unchecked`](hb::HashMap::insert_unique_unchecked) for further details.1203///1204/// # Safety1205///1206/// This operation is safe if a key does not exist in the map.1207///1208/// However, if a key exists in the map already, the behavior is unspecified:1209/// this operation may panic, loop forever, or any following operation with the map1210/// may panic, loop forever or return arbitrary result.1211///1212/// That said, this operation (and following operations) are guaranteed to1213/// not violate memory safety.1214///1215/// However this operation is still unsafe because the resulting `HashMap`1216/// may be passed to unsafe code which does expect the map to behave1217/// correctly, and would cause unsoundness as a result.1218#[expect(1219unsafe_code,1220reason = "re-exporting unsafe method from Hashbrown requires unsafe code"1221)]1222#[inline]1223pub unsafe fn insert_unique_unchecked(&mut self, key: K, value: V) -> (&K, &mut V) {1224// SAFETY: safety contract is ensured by the caller.1225unsafe { self.0.insert_unique_unchecked(key, value) }1226}12271228/// Attempts to get mutable references to `N` values in the map at once, without validating that1229/// the values are unique.1230///1231/// Refer to [`get_disjoint_unchecked_mut`](hb::HashMap::get_disjoint_unchecked_mut) for further details.1232///1233/// Returns an array of length `N` with the results of each query. `None` will be used if1234/// the key is missing.1235///1236/// For a safe alternative see [`get_disjoint_mut`](`HashMap::get_disjoint_mut`).1237///1238/// # Safety1239///1240/// Calling this method with overlapping keys is *[undefined behavior]* even if the resulting1241/// references are not used.1242///1243/// [undefined behavior]: https://doc.rust-lang.org/reference/behavior-considered-undefined.html1244#[expect(1245unsafe_code,1246reason = "re-exporting unsafe method from Hashbrown requires unsafe code"1247)]1248#[inline]1249pub unsafe fn get_disjoint_unchecked_mut<Q, const N: usize>(1250&mut self,1251keys: [&Q; N],1252) -> [Option<&'_ mut V>; N]1253where1254Q: Hash + Equivalent<K> + ?Sized,1255{1256// SAFETY: safety contract is ensured by the caller.1257unsafe { self.0.get_disjoint_unchecked_mut(keys) }1258}12591260/// Attempts to get mutable references to `N` values in the map at once, with immutable1261/// references to the corresponding keys, without validating that the values are unique.1262///1263/// Refer to [`get_disjoint_key_value_unchecked_mut`](hb::HashMap::get_disjoint_key_value_unchecked_mut) for further details.1264///1265/// Returns an array of length `N` with the results of each query. `None` will be returned if1266/// any of the keys are missing.1267///1268/// For a safe alternative see [`get_disjoint_key_value_mut`](`HashMap::get_disjoint_key_value_mut`).1269///1270/// # Safety1271///1272/// Calling this method with overlapping keys is *[undefined behavior]* even if the resulting1273/// references are not used.1274///1275/// [undefined behavior]: https://doc.rust-lang.org/reference/behavior-considered-undefined.html1276#[expect(1277unsafe_code,1278reason = "re-exporting unsafe method from Hashbrown requires unsafe code"1279)]1280#[inline]1281pub unsafe fn get_disjoint_key_value_unchecked_mut<Q, const N: usize>(1282&mut self,1283keys: [&Q; N],1284) -> [Option<(&'_ K, &'_ mut V)>; N]1285where1286Q: Hash + Equivalent<K> + ?Sized,1287{1288// SAFETY: safety contract is ensured by the caller.1289unsafe { self.0.get_disjoint_key_value_unchecked_mut(keys) }1290}1291}129212931294