jam_types/
vec_map.rs

1use super::*;
2use codec::Error as DecodeError;
3use core::fmt;
4
5/// A data-structure providing the storage and lookup of key/value pairs with exclusive keys.
6pub trait MapLike<K, V> {
7	/// Insert pair into the mapping.
8	///
9	/// Inserts some pair (`k`, `v`) into the mapping, replacing the existing pair whose key is `k`,
10	/// if any.
11	///
12	/// Returns [Some] value which was replaced, if any.
13	fn insert(&mut self, k: K, v: V) -> Option<V>;
14	/// Insert multiple pairs from an iterator.
15	///
16	/// Replaces any existing pairs which share a key with an element of the iterator.
17	fn extend(&mut self, iter: impl Iterator<Item = (K, V)>);
18	/// Check if a key is in the mapping.
19	///
20	/// Returns `true` iff the mapping contains a pair whose key equals `k`.
21	fn contains_key(&self, k: &K) -> bool;
22	/// Remove an item from the mapping by key.
23	///
24	/// Removes the item with key equal to `k` from the mapping.
25	///
26	/// Returns the value of the item removed, if any.
27	fn remove(&mut self, k: &K) -> Option<V>;
28	/// Get the value of the pair with a particular key.
29	///
30	/// Returns a reference the value of the item in the mapping whose key equals `k`.
31	fn get(&self, k: &K) -> Option<&V>;
32	/// Get a mutable reference to the value of the pair with a particular key.
33	///
34	/// Returns a mutable reference the value of the item in the mapping whose key equals `k`.
35	fn get_mut(&mut self, k: &K) -> Option<&mut V>;
36	/// Get an iterator to all keys in the mapping.
37	///
38	/// No order is guaranteed.
39	fn keys<'a>(&'a self) -> impl Iterator<Item = &'a K>
40	where
41		K: 'a;
42}
43
44#[cfg(feature = "std")]
45impl<K: Eq + std::hash::Hash, V> MapLike<K, V> for std::collections::HashMap<K, V> {
46	fn insert(&mut self, k: K, v: V) -> Option<V> {
47		std::collections::HashMap::<K, V>::insert(self, k, v)
48	}
49	fn extend(&mut self, iter: impl Iterator<Item = (K, V)>) {
50		<std::collections::HashMap<K, V> as Extend<(K, V)>>::extend(self, iter)
51	}
52	fn contains_key(&self, k: &K) -> bool {
53		std::collections::HashMap::<K, V>::contains_key(self, k)
54	}
55	fn remove(&mut self, k: &K) -> Option<V> {
56		std::collections::HashMap::<K, V>::remove(self, k)
57	}
58	fn get(&self, k: &K) -> Option<&V> {
59		std::collections::HashMap::<K, V>::get(self, k)
60	}
61	fn get_mut(&mut self, k: &K) -> Option<&mut V> {
62		std::collections::HashMap::<K, V>::get_mut(self, k)
63	}
64	fn keys<'a>(&'a self) -> impl Iterator<Item = &'a K>
65	where
66		K: 'a,
67	{
68		std::collections::HashMap::<K, V>::keys(self)
69	}
70}
71
72impl<K: Eq + PartialEq + Ord + PartialOrd, V> MapLike<K, V> for alloc::collections::BTreeMap<K, V> {
73	fn insert(&mut self, k: K, v: V) -> Option<V> {
74		alloc::collections::BTreeMap::<K, V>::insert(self, k, v)
75	}
76	fn extend(&mut self, iter: impl Iterator<Item = (K, V)>) {
77		<alloc::collections::BTreeMap<K, V> as Extend<(K, V)>>::extend(self, iter)
78	}
79	fn contains_key(&self, k: &K) -> bool {
80		alloc::collections::BTreeMap::<K, V>::contains_key(self, k)
81	}
82	fn remove(&mut self, k: &K) -> Option<V> {
83		alloc::collections::BTreeMap::<K, V>::remove(self, k)
84	}
85	fn get(&self, k: &K) -> Option<&V> {
86		alloc::collections::BTreeMap::<K, V>::get(self, k)
87	}
88	fn get_mut(&mut self, k: &K) -> Option<&mut V> {
89		alloc::collections::BTreeMap::<K, V>::get_mut(self, k)
90	}
91	fn keys<'a>(&'a self) -> impl Iterator<Item = &'a K>
92	where
93		K: 'a,
94	{
95		alloc::collections::BTreeMap::<K, V>::keys(self)
96	}
97}
98
99/// An mapping of key/value pairs stored as pairs ordered by their key in a [Vec].
100///
101/// This is always efficient for small sizes of mappings, and efficient for large sizes when
102/// insertion is not needed (i.e. items are placed into the mapping in bulk).
103#[derive(Clone, Encode, Eq, PartialEq, Ord, PartialOrd)]
104pub struct VecMap<K, V>(Vec<(K, V)>);
105impl<K: Eq + PartialEq + Ord + PartialOrd, V> VecMap<K, V> {
106	/// Create a new, empty instance.
107	pub fn new() -> Self {
108		Self(Vec::new())
109	}
110	/// Create a new instance from a sorted [Vec].
111	///
112	/// Returns [Ok] with an instance containing the same items as `v`, or [Err] if `v` is unsorted.
113	pub fn from_sorted(v: Vec<(K, V)>) -> Result<Self, ()> {
114		let Some((first, _)) = v.first() else { return Ok(Self::new()) };
115		v.iter()
116			.skip(1)
117			.try_fold(first, |a, (e, _)| if a < e { Some(e) } else { None })
118			.ok_or(())?;
119		Ok(Self(v))
120	}
121	/// Return the number of items this mapping contains.
122	pub fn len(&self) -> usize {
123		self.0.len()
124	}
125	/// Return `true` if this mapping is empty.
126	pub fn is_empty(&self) -> bool {
127		self.0.is_empty()
128	}
129	/// Return an iterator over the key/value pairs in this mapping in order.
130	pub fn iter(&self) -> core::slice::Iter<(K, V)> {
131		self.0.iter()
132	}
133	/// Return an iterator over the keys in this mapping in order.
134	pub fn keys(&self) -> impl Iterator<Item = &K> {
135		self.0.iter().map(|(k, _)| k)
136	}
137	/// Return an iterator over the values in this mapping in order of their corresponding key.
138	pub fn values(&self) -> impl Iterator<Item = &V> {
139		self.0.iter().map(|(_, v)| v)
140	}
141	/// Get the value of the pair with a particular key.
142	///
143	/// Returns a reference the value of the item in the mapping whose key equals `k`.
144	pub fn get(&self, k: &K) -> Option<&V> {
145		self.0.binary_search_by(|x| x.0.cmp(k)).ok().map(|i| &self.0[i].1)
146	}
147	/// Get a mutable reference to the value of the pair with a particular key.
148	///
149	/// Returns a mutable reference the value of the item in the mapping whose key equals `k`.
150	pub fn get_mut(&mut self, k: &K) -> Option<&mut V> {
151		self.0.binary_search_by(|x| x.0.cmp(k)).ok().map(move |i| &mut self.0[i].1)
152	}
153	/// Consume this mapping and return a [Vec] of transformed pairs.
154	///
155	/// Returns the [Vec] of the resultant values of applying `f` to each pair in the mapping in
156	/// order.
157	pub fn map<U>(self, mut f: impl FnMut(K, V) -> U) -> Vec<U> {
158		self.0.into_iter().map(|(k, v)| f(k, v)).collect::<Vec<_>>()
159	}
160	/// Transform all pairs by reference and return a [Vec] with the results.
161	///
162	/// Returns the [Vec] of the resultant values of applying `f` to each pair by reference in the
163	/// mapping in order.
164	pub fn map_ref<U>(&self, mut f: impl FnMut(&K, &V) -> U) -> Vec<U> {
165		self.0.iter().map(|(k, v)| f(k, v)).collect::<Vec<_>>()
166	}
167	/// Return a [Vec] of sorted key/value pairs by cloning this mapping.
168	pub fn to_vec(&self) -> Vec<(K, V)>
169	where
170		K: Clone,
171		V: Clone,
172	{
173		self.0.clone()
174	}
175	/// Return the [Vec] of sorted key/value pairs by consuming this mapping.
176	pub fn into_vec(self) -> Vec<(K, V)> {
177		self.0
178	}
179	/// Insert pair into the mapping.
180	///
181	/// Inserts some pair (`k`, `v`) into the mapping, replacing the existing pair whose key is `k`,
182	/// if any.
183	///
184	/// Returns [Some] value which was replaced, if any.
185	///
186	/// NOTE: This does an ordered insert and thus is slow. If you're inserting multiple items, use
187	/// [Self::extend] which is much more efficient or consider using an alternative data structure
188	/// if you're doing this a lot.
189	pub fn insert(&mut self, k: K, v: V) -> Option<(K, V)> {
190		match self.0.binary_search_by(|x| x.0.cmp(&k)) {
191			Ok(i) => Some(core::mem::replace(&mut self.0[i], (k, v))),
192			Err(i) => {
193				self.0.insert(i, (k, v));
194				None
195			},
196		}
197	}
198	/// Insert multiple pairs from an iterator.
199	///
200	/// Replaces any existing pairs which share a key with an element of the iterator.
201	pub fn extend(&mut self, iter: impl IntoIterator<Item = (K, V)>) {
202		self.0.splice(0..0, iter);
203		self.0.sort_by(|x, y| x.0.cmp(&y.0));
204		self.0.dedup_by(|x, y| x.0 == y.0);
205	}
206	/// Check if a key is in the mapping.
207	///
208	/// Returns `true` iff the mapping contains a pair whose key equals `k`.
209	pub fn contains_key(&self, k: &K) -> bool {
210		self.0.binary_search_by(|x| x.0.cmp(k)).is_ok()
211	}
212	/// Remove an item from the mapping by key.
213	///
214	/// Removes the item with key equal to `k` from the mapping.
215	///
216	/// Returns the value of the item removed, if any.
217	pub fn remove(&mut self, k: &K) -> Option<(K, V)> {
218		match self.0.binary_search_by(|x| x.0.cmp(k)) {
219			Ok(i) => Some(self.0.remove(i)),
220			Err(_) => None,
221		}
222	}
223	/// Filter items from the mapping.
224	///
225	/// Removes all pairs from the mapping for which `f` returns `false`.
226	pub fn retain(&mut self, mut f: impl FnMut(&K, &V) -> bool) {
227		self.0.retain(|x| f(&x.0, &x.1));
228	}
229	// TODO: Create traits `OrderedSetLike`/`OrderedMapLike` and make work with them.
230	/// Compares the pairs in two mappings.
231	///
232	/// Returns `true` iff every pair in the mapping is not found in `other`.
233	pub fn is_disjoint(&self, other: &VecMap<K, V>) -> bool
234	where
235		V: Ord,
236	{
237		vec_set::is_disjoint(self.iter(), other.iter())
238	}
239	/// Compares the keys in two mappings.
240	///
241	/// Returns `true` iff every key in the mapping is not found in the keys of `other`.
242	pub fn keys_disjoint<W>(&self, other: &VecMap<K, W>) -> bool {
243		vec_set::is_disjoint(self.keys(), other.keys())
244	}
245	/// Compares the keys in this mapping with the values in a set.
246	///
247	/// Returns `true` iff every key in the mapping is not found in `other`.
248	pub fn keys_disjoint_with_set(&self, other: &VecSet<K>) -> bool {
249		vec_set::is_disjoint(self.keys(), other.iter())
250	}
251}
252
253impl<K: Eq + PartialEq + Ord + PartialOrd, V> MapLike<K, V> for VecMap<K, V> {
254	fn insert(&mut self, k: K, v: V) -> Option<V> {
255		VecMap::<K, V>::insert(self, k, v).map(|(_, v)| v)
256	}
257	fn extend(&mut self, iter: impl Iterator<Item = (K, V)>) {
258		VecMap::<K, V>::extend(self, iter)
259	}
260	fn contains_key(&self, k: &K) -> bool {
261		VecMap::<K, V>::contains_key(self, k)
262	}
263	fn remove(&mut self, k: &K) -> Option<V> {
264		VecMap::<K, V>::remove(self, k).map(|x| x.1)
265	}
266	fn get(&self, k: &K) -> Option<&V> {
267		VecMap::<K, V>::get(self, k)
268	}
269	fn get_mut(&mut self, k: &K) -> Option<&mut V> {
270		VecMap::<K, V>::get_mut(self, k)
271	}
272	fn keys<'a>(&'a self) -> impl Iterator<Item = &'a K>
273	where
274		K: 'a,
275	{
276		VecMap::<K, V>::keys(self)
277	}
278}
279
280impl<K: fmt::Debug, V: fmt::Debug> fmt::Debug for VecMap<K, V> {
281	fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
282		match self.0.len() {
283			0 => write!(f, "[]"),
284			_ => {
285				write!(f, "[{:?}=>{:?}", self.0[0].0, self.0[0].1)?;
286				for i in 1..self.0.len() {
287					write!(f, ", {:?}=>{:?}", self.0[i].0, self.0[i].1)?;
288				}
289				write!(f, "]")
290			},
291		}
292	}
293}
294
295impl<K: fmt::Display, V: fmt::Display> fmt::Display for VecMap<K, V> {
296	fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
297		match self.0.len() {
298			0 => write!(f, "[]"),
299			_ => {
300				write!(f, "[{}=>{}", self.0[0].0, self.0[0].1)?;
301				for i in 1..self.0.len() {
302					write!(f, ", {}=>{}", self.0[i].0, self.0[i].1)?;
303				}
304				write!(f, "]")
305			},
306		}
307	}
308}
309
310impl<K: Decode + Eq + PartialEq + Ord + PartialOrd, V: Decode> Decode for VecMap<K, V> {
311	fn decode<I: codec::Input>(input: &mut I) -> Result<Self, DecodeError> {
312		Ok(Self::from_sorted(Vec::<(K, V)>::decode(input)?).map_err(|()| "set out-of-order")?)
313	}
314}
315
316impl<K, V> Default for VecMap<K, V> {
317	fn default() -> Self {
318		Self(Vec::new())
319	}
320}
321impl<K, V> AsRef<[(K, V)]> for VecMap<K, V> {
322	fn as_ref(&self) -> &[(K, V)] {
323		&self.0[..]
324	}
325}
326impl<K, V> AsMut<[(K, V)]> for VecMap<K, V> {
327	fn as_mut(&mut self) -> &mut [(K, V)] {
328		&mut self.0[..]
329	}
330}
331
332impl<K, V> From<VecMap<K, V>> for Vec<(K, V)> {
333	fn from(s: VecMap<K, V>) -> Vec<(K, V)> {
334		s.0
335	}
336}
337impl<K: Eq + PartialEq + Ord + PartialOrd, V> From<Vec<(K, V)>> for VecMap<K, V> {
338	fn from(mut v: Vec<(K, V)>) -> Self {
339		v.sort_by(|x, y| x.0.cmp(&y.0));
340		v.dedup_by(|x, y| x.0 == y.0);
341		Self(v)
342	}
343}
344impl<K: Eq + PartialEq + Ord + PartialOrd, V> FromIterator<(K, V)> for VecMap<K, V> {
345	fn from_iter<I: IntoIterator<Item = (K, V)>>(iter: I) -> Self {
346		Vec::<(K, V)>::from_iter(iter).into()
347	}
348}
349impl<K: Eq + PartialEq + Ord + PartialOrd, V> Extend<(K, V)> for VecMap<K, V> {
350	fn extend<I: IntoIterator<Item = (K, V)>>(&mut self, iter: I) {
351		VecMap::<K, V>::extend(self, iter)
352	}
353}
354impl<K: Eq + PartialEq + Ord + PartialOrd, V> IntoIterator for VecMap<K, V> {
355	type Item = (K, V);
356	type IntoIter = <Vec<(K, V)> as IntoIterator>::IntoIter;
357
358	fn into_iter(self) -> Self::IntoIter {
359		self.0.into_iter()
360	}
361}
362
363#[cfg(test)]
364mod tests {
365	use super::*;
366	#[test]
367	fn encode_decode_works() {
368		let v = VecMap::<u32, u32>::from_iter((0..100).map(|j| ((j * 97) % 101, j)));
369		println!("{}", v);
370		let e = v.encode();
371		let d = VecMap::<u32, u32>::decode(&mut &e[..]).unwrap();
372		assert_eq!(v, d);
373	}
374}