1 | use super::{ |
2 | Bucket, Entries, IndexMap, IntoIter, IntoKeys, IntoValues, Iter, IterMut, Keys, Values, |
3 | ValuesMut, |
4 | }; |
5 | use crate::util::{slice_eq, try_simplify_range}; |
6 | use crate::GetDisjointMutError; |
7 | |
8 | use alloc::boxed::Box; |
9 | use alloc::vec::Vec; |
10 | use core::cmp::Ordering; |
11 | use core::fmt; |
12 | use core::hash::{Hash, Hasher}; |
13 | use core::ops::{self, Bound, Index, IndexMut, RangeBounds}; |
14 | |
15 | /// A dynamically-sized slice of key-value pairs in an [`IndexMap`]. |
16 | /// |
17 | /// This supports indexed operations much like a `[(K, V)]` slice, |
18 | /// but not any hashed operations on the map keys. |
19 | /// |
20 | /// Unlike `IndexMap`, `Slice` does consider the order for [`PartialEq`] |
21 | /// and [`Eq`], and it also implements [`PartialOrd`], [`Ord`], and [`Hash`]. |
22 | #[repr (transparent)] |
23 | pub struct Slice<K, V> { |
24 | pub(crate) entries: [Bucket<K, V>], |
25 | } |
26 | |
27 | // SAFETY: `Slice<K, V>` is a transparent wrapper around `[Bucket<K, V>]`, |
28 | // and reference lifetimes are bound together in function signatures. |
29 | #[allow (unsafe_code)] |
30 | impl<K, V> Slice<K, V> { |
31 | pub(super) const fn from_slice(entries: &[Bucket<K, V>]) -> &Self { |
32 | unsafe { &*(entries as *const [Bucket<K, V>] as *const Self) } |
33 | } |
34 | |
35 | pub(super) fn from_mut_slice(entries: &mut [Bucket<K, V>]) -> &mut Self { |
36 | unsafe { &mut *(entries as *mut [Bucket<K, V>] as *mut Self) } |
37 | } |
38 | |
39 | pub(super) fn from_boxed(entries: Box<[Bucket<K, V>]>) -> Box<Self> { |
40 | unsafe { Box::from_raw(Box::into_raw(entries) as *mut Self) } |
41 | } |
42 | |
43 | fn into_boxed(self: Box<Self>) -> Box<[Bucket<K, V>]> { |
44 | unsafe { Box::from_raw(Box::into_raw(self) as *mut [Bucket<K, V>]) } |
45 | } |
46 | } |
47 | |
48 | impl<K, V> Slice<K, V> { |
49 | pub(crate) fn into_entries(self: Box<Self>) -> Vec<Bucket<K, V>> { |
50 | self.into_boxed().into_vec() |
51 | } |
52 | |
53 | /// Returns an empty slice. |
54 | pub const fn new<'a>() -> &'a Self { |
55 | Self::from_slice(&[]) |
56 | } |
57 | |
58 | /// Returns an empty mutable slice. |
59 | pub fn new_mut<'a>() -> &'a mut Self { |
60 | Self::from_mut_slice(&mut []) |
61 | } |
62 | |
63 | /// Return the number of key-value pairs in the map slice. |
64 | #[inline ] |
65 | pub const fn len(&self) -> usize { |
66 | self.entries.len() |
67 | } |
68 | |
69 | /// Returns true if the map slice contains no elements. |
70 | #[inline ] |
71 | pub const fn is_empty(&self) -> bool { |
72 | self.entries.is_empty() |
73 | } |
74 | |
75 | /// Get a key-value pair by index. |
76 | /// |
77 | /// Valid indices are `0 <= index < self.len()`. |
78 | pub fn get_index(&self, index: usize) -> Option<(&K, &V)> { |
79 | self.entries.get(index).map(Bucket::refs) |
80 | } |
81 | |
82 | /// Get a key-value pair by index, with mutable access to the value. |
83 | /// |
84 | /// Valid indices are `0 <= index < self.len()`. |
85 | pub fn get_index_mut(&mut self, index: usize) -> Option<(&K, &mut V)> { |
86 | self.entries.get_mut(index).map(Bucket::ref_mut) |
87 | } |
88 | |
89 | /// Returns a slice of key-value pairs in the given range of indices. |
90 | /// |
91 | /// Valid indices are `0 <= index < self.len()`. |
92 | pub fn get_range<R: RangeBounds<usize>>(&self, range: R) -> Option<&Self> { |
93 | let range = try_simplify_range(range, self.entries.len())?; |
94 | self.entries.get(range).map(Slice::from_slice) |
95 | } |
96 | |
97 | /// Returns a mutable slice of key-value pairs in the given range of indices. |
98 | /// |
99 | /// Valid indices are `0 <= index < self.len()`. |
100 | pub fn get_range_mut<R: RangeBounds<usize>>(&mut self, range: R) -> Option<&mut Self> { |
101 | let range = try_simplify_range(range, self.entries.len())?; |
102 | self.entries.get_mut(range).map(Slice::from_mut_slice) |
103 | } |
104 | |
105 | /// Get the first key-value pair. |
106 | pub fn first(&self) -> Option<(&K, &V)> { |
107 | self.entries.first().map(Bucket::refs) |
108 | } |
109 | |
110 | /// Get the first key-value pair, with mutable access to the value. |
111 | pub fn first_mut(&mut self) -> Option<(&K, &mut V)> { |
112 | self.entries.first_mut().map(Bucket::ref_mut) |
113 | } |
114 | |
115 | /// Get the last key-value pair. |
116 | pub fn last(&self) -> Option<(&K, &V)> { |
117 | self.entries.last().map(Bucket::refs) |
118 | } |
119 | |
120 | /// Get the last key-value pair, with mutable access to the value. |
121 | pub fn last_mut(&mut self) -> Option<(&K, &mut V)> { |
122 | self.entries.last_mut().map(Bucket::ref_mut) |
123 | } |
124 | |
125 | /// Divides one slice into two at an index. |
126 | /// |
127 | /// ***Panics*** if `index > len`. |
128 | pub fn split_at(&self, index: usize) -> (&Self, &Self) { |
129 | let (first, second) = self.entries.split_at(index); |
130 | (Self::from_slice(first), Self::from_slice(second)) |
131 | } |
132 | |
133 | /// Divides one mutable slice into two at an index. |
134 | /// |
135 | /// ***Panics*** if `index > len`. |
136 | pub fn split_at_mut(&mut self, index: usize) -> (&mut Self, &mut Self) { |
137 | let (first, second) = self.entries.split_at_mut(index); |
138 | (Self::from_mut_slice(first), Self::from_mut_slice(second)) |
139 | } |
140 | |
141 | /// Returns the first key-value pair and the rest of the slice, |
142 | /// or `None` if it is empty. |
143 | pub fn split_first(&self) -> Option<((&K, &V), &Self)> { |
144 | if let [first, rest @ ..] = &self.entries { |
145 | Some((first.refs(), Self::from_slice(rest))) |
146 | } else { |
147 | None |
148 | } |
149 | } |
150 | |
151 | /// Returns the first key-value pair and the rest of the slice, |
152 | /// with mutable access to the value, or `None` if it is empty. |
153 | pub fn split_first_mut(&mut self) -> Option<((&K, &mut V), &mut Self)> { |
154 | if let [first, rest @ ..] = &mut self.entries { |
155 | Some((first.ref_mut(), Self::from_mut_slice(rest))) |
156 | } else { |
157 | None |
158 | } |
159 | } |
160 | |
161 | /// Returns the last key-value pair and the rest of the slice, |
162 | /// or `None` if it is empty. |
163 | pub fn split_last(&self) -> Option<((&K, &V), &Self)> { |
164 | if let [rest @ .., last] = &self.entries { |
165 | Some((last.refs(), Self::from_slice(rest))) |
166 | } else { |
167 | None |
168 | } |
169 | } |
170 | |
171 | /// Returns the last key-value pair and the rest of the slice, |
172 | /// with mutable access to the value, or `None` if it is empty. |
173 | pub fn split_last_mut(&mut self) -> Option<((&K, &mut V), &mut Self)> { |
174 | if let [rest @ .., last] = &mut self.entries { |
175 | Some((last.ref_mut(), Self::from_mut_slice(rest))) |
176 | } else { |
177 | None |
178 | } |
179 | } |
180 | |
181 | /// Return an iterator over the key-value pairs of the map slice. |
182 | pub fn iter(&self) -> Iter<'_, K, V> { |
183 | Iter::new(&self.entries) |
184 | } |
185 | |
186 | /// Return an iterator over the key-value pairs of the map slice. |
187 | pub fn iter_mut(&mut self) -> IterMut<'_, K, V> { |
188 | IterMut::new(&mut self.entries) |
189 | } |
190 | |
191 | /// Return an iterator over the keys of the map slice. |
192 | pub fn keys(&self) -> Keys<'_, K, V> { |
193 | Keys::new(&self.entries) |
194 | } |
195 | |
196 | /// Return an owning iterator over the keys of the map slice. |
197 | pub fn into_keys(self: Box<Self>) -> IntoKeys<K, V> { |
198 | IntoKeys::new(self.into_entries()) |
199 | } |
200 | |
201 | /// Return an iterator over the values of the map slice. |
202 | pub fn values(&self) -> Values<'_, K, V> { |
203 | Values::new(&self.entries) |
204 | } |
205 | |
206 | /// Return an iterator over mutable references to the the values of the map slice. |
207 | pub fn values_mut(&mut self) -> ValuesMut<'_, K, V> { |
208 | ValuesMut::new(&mut self.entries) |
209 | } |
210 | |
211 | /// Return an owning iterator over the values of the map slice. |
212 | pub fn into_values(self: Box<Self>) -> IntoValues<K, V> { |
213 | IntoValues::new(self.into_entries()) |
214 | } |
215 | |
216 | /// Search over a sorted map for a key. |
217 | /// |
218 | /// Returns the position where that key is present, or the position where it can be inserted to |
219 | /// maintain the sort. See [`slice::binary_search`] for more details. |
220 | /// |
221 | /// Computes in **O(log(n))** time, which is notably less scalable than looking the key up in |
222 | /// the map this is a slice from using [`IndexMap::get_index_of`], but this can also position |
223 | /// missing keys. |
224 | pub fn binary_search_keys(&self, x: &K) -> Result<usize, usize> |
225 | where |
226 | K: Ord, |
227 | { |
228 | self.binary_search_by(|p, _| p.cmp(x)) |
229 | } |
230 | |
231 | /// Search over a sorted map with a comparator function. |
232 | /// |
233 | /// Returns the position where that value is present, or the position where it can be inserted |
234 | /// to maintain the sort. See [`slice::binary_search_by`] for more details. |
235 | /// |
236 | /// Computes in **O(log(n))** time. |
237 | #[inline ] |
238 | pub fn binary_search_by<'a, F>(&'a self, mut f: F) -> Result<usize, usize> |
239 | where |
240 | F: FnMut(&'a K, &'a V) -> Ordering, |
241 | { |
242 | self.entries.binary_search_by(move |a| f(&a.key, &a.value)) |
243 | } |
244 | |
245 | /// Search over a sorted map with an extraction function. |
246 | /// |
247 | /// Returns the position where that value is present, or the position where it can be inserted |
248 | /// to maintain the sort. See [`slice::binary_search_by_key`] for more details. |
249 | /// |
250 | /// Computes in **O(log(n))** time. |
251 | #[inline ] |
252 | pub fn binary_search_by_key<'a, B, F>(&'a self, b: &B, mut f: F) -> Result<usize, usize> |
253 | where |
254 | F: FnMut(&'a K, &'a V) -> B, |
255 | B: Ord, |
256 | { |
257 | self.binary_search_by(|k, v| f(k, v).cmp(b)) |
258 | } |
259 | |
260 | /// Returns the index of the partition point of a sorted map according to the given predicate |
261 | /// (the index of the first element of the second partition). |
262 | /// |
263 | /// See [`slice::partition_point`] for more details. |
264 | /// |
265 | /// Computes in **O(log(n))** time. |
266 | #[must_use ] |
267 | pub fn partition_point<P>(&self, mut pred: P) -> usize |
268 | where |
269 | P: FnMut(&K, &V) -> bool, |
270 | { |
271 | self.entries |
272 | .partition_point(move |a| pred(&a.key, &a.value)) |
273 | } |
274 | |
275 | /// Get an array of `N` key-value pairs by `N` indices |
276 | /// |
277 | /// Valid indices are *0 <= index < self.len()* and each index needs to be unique. |
278 | pub fn get_disjoint_mut<const N: usize>( |
279 | &mut self, |
280 | indices: [usize; N], |
281 | ) -> Result<[(&K, &mut V); N], GetDisjointMutError> { |
282 | let indices = indices.map(Some); |
283 | let key_values = self.get_disjoint_opt_mut(indices)?; |
284 | Ok(key_values.map(Option::unwrap)) |
285 | } |
286 | |
287 | #[allow (unsafe_code)] |
288 | pub(crate) fn get_disjoint_opt_mut<const N: usize>( |
289 | &mut self, |
290 | indices: [Option<usize>; N], |
291 | ) -> Result<[Option<(&K, &mut V)>; N], GetDisjointMutError> { |
292 | // SAFETY: Can't allow duplicate indices as we would return several mutable refs to the same data. |
293 | let len = self.len(); |
294 | for i in 0..N { |
295 | if let Some(idx) = indices[i] { |
296 | if idx >= len { |
297 | return Err(GetDisjointMutError::IndexOutOfBounds); |
298 | } else if indices[..i].contains(&Some(idx)) { |
299 | return Err(GetDisjointMutError::OverlappingIndices); |
300 | } |
301 | } |
302 | } |
303 | |
304 | let entries_ptr = self.entries.as_mut_ptr(); |
305 | let out = indices.map(|idx_opt| { |
306 | match idx_opt { |
307 | Some(idx) => { |
308 | // SAFETY: The base pointer is valid as it comes from a slice and the reference is always |
309 | // in-bounds & unique as we've already checked the indices above. |
310 | let kv = unsafe { (*(entries_ptr.add(idx))).ref_mut() }; |
311 | Some(kv) |
312 | } |
313 | None => None, |
314 | } |
315 | }); |
316 | |
317 | Ok(out) |
318 | } |
319 | } |
320 | |
321 | impl<'a, K, V> IntoIterator for &'a Slice<K, V> { |
322 | type IntoIter = Iter<'a, K, V>; |
323 | type Item = (&'a K, &'a V); |
324 | |
325 | fn into_iter(self) -> Self::IntoIter { |
326 | self.iter() |
327 | } |
328 | } |
329 | |
330 | impl<'a, K, V> IntoIterator for &'a mut Slice<K, V> { |
331 | type IntoIter = IterMut<'a, K, V>; |
332 | type Item = (&'a K, &'a mut V); |
333 | |
334 | fn into_iter(self) -> Self::IntoIter { |
335 | self.iter_mut() |
336 | } |
337 | } |
338 | |
339 | impl<K, V> IntoIterator for Box<Slice<K, V>> { |
340 | type IntoIter = IntoIter<K, V>; |
341 | type Item = (K, V); |
342 | |
343 | fn into_iter(self) -> Self::IntoIter { |
344 | IntoIter::new(self.into_entries()) |
345 | } |
346 | } |
347 | |
348 | impl<K, V> Default for &'_ Slice<K, V> { |
349 | fn default() -> Self { |
350 | Slice::from_slice(&[]) |
351 | } |
352 | } |
353 | |
354 | impl<K, V> Default for &'_ mut Slice<K, V> { |
355 | fn default() -> Self { |
356 | Slice::from_mut_slice(&mut []) |
357 | } |
358 | } |
359 | |
360 | impl<K, V> Default for Box<Slice<K, V>> { |
361 | fn default() -> Self { |
362 | Slice::from_boxed(entries:Box::default()) |
363 | } |
364 | } |
365 | |
366 | impl<K: Clone, V: Clone> Clone for Box<Slice<K, V>> { |
367 | fn clone(&self) -> Self { |
368 | Slice::from_boxed(self.entries.to_vec().into_boxed_slice()) |
369 | } |
370 | } |
371 | |
372 | impl<K: Copy, V: Copy> From<&Slice<K, V>> for Box<Slice<K, V>> { |
373 | fn from(slice: &Slice<K, V>) -> Self { |
374 | Slice::from_boxed(entries:Box::from(&slice.entries)) |
375 | } |
376 | } |
377 | |
378 | impl<K: fmt::Debug, V: fmt::Debug> fmt::Debug for Slice<K, V> { |
379 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { |
380 | f.debug_list().entries(self).finish() |
381 | } |
382 | } |
383 | |
384 | impl<K, V, K2, V2> PartialEq<Slice<K2, V2>> for Slice<K, V> |
385 | where |
386 | K: PartialEq<K2>, |
387 | V: PartialEq<V2>, |
388 | { |
389 | fn eq(&self, other: &Slice<K2, V2>) -> bool { |
390 | slice_eq(&self.entries, &other.entries, |b1: &Bucket, b2: &Bucket| { |
391 | b1.key == b2.key && b1.value == b2.value |
392 | }) |
393 | } |
394 | } |
395 | |
396 | impl<K, V, K2, V2> PartialEq<[(K2, V2)]> for Slice<K, V> |
397 | where |
398 | K: PartialEq<K2>, |
399 | V: PartialEq<V2>, |
400 | { |
401 | fn eq(&self, other: &[(K2, V2)]) -> bool { |
402 | slice_eq(&self.entries, right:other, |b: &Bucket, t: &(K2, V2)| b.key == t.0 && b.value == t.1) |
403 | } |
404 | } |
405 | |
406 | impl<K, V, K2, V2> PartialEq<Slice<K2, V2>> for [(K, V)] |
407 | where |
408 | K: PartialEq<K2>, |
409 | V: PartialEq<V2>, |
410 | { |
411 | fn eq(&self, other: &Slice<K2, V2>) -> bool { |
412 | slice_eq(self, &other.entries, |t: &(K, V), b: &Bucket| t.0 == b.key && t.1 == b.value) |
413 | } |
414 | } |
415 | |
416 | impl<K, V, K2, V2, const N: usize> PartialEq<[(K2, V2); N]> for Slice<K, V> |
417 | where |
418 | K: PartialEq<K2>, |
419 | V: PartialEq<V2>, |
420 | { |
421 | fn eq(&self, other: &[(K2, V2); N]) -> bool { |
422 | <Self as PartialEq<[_]>>::eq(self, other) |
423 | } |
424 | } |
425 | |
426 | impl<K, V, const N: usize, K2, V2> PartialEq<Slice<K2, V2>> for [(K, V); N] |
427 | where |
428 | K: PartialEq<K2>, |
429 | V: PartialEq<V2>, |
430 | { |
431 | fn eq(&self, other: &Slice<K2, V2>) -> bool { |
432 | <[_] as PartialEq<_>>::eq(self, other) |
433 | } |
434 | } |
435 | |
436 | impl<K: Eq, V: Eq> Eq for Slice<K, V> {} |
437 | |
438 | impl<K: PartialOrd, V: PartialOrd> PartialOrd for Slice<K, V> { |
439 | fn partial_cmp(&self, other: &Self) -> Option<Ordering> { |
440 | self.iter().partial_cmp(other) |
441 | } |
442 | } |
443 | |
444 | impl<K: Ord, V: Ord> Ord for Slice<K, V> { |
445 | fn cmp(&self, other: &Self) -> Ordering { |
446 | self.iter().cmp(other) |
447 | } |
448 | } |
449 | |
450 | impl<K: Hash, V: Hash> Hash for Slice<K, V> { |
451 | fn hash<H: Hasher>(&self, state: &mut H) { |
452 | self.len().hash(state); |
453 | for (key: &K, value: &V) in self { |
454 | key.hash(state); |
455 | value.hash(state); |
456 | } |
457 | } |
458 | } |
459 | |
460 | impl<K, V> Index<usize> for Slice<K, V> { |
461 | type Output = V; |
462 | |
463 | fn index(&self, index: usize) -> &V { |
464 | &self.entries[index].value |
465 | } |
466 | } |
467 | |
468 | impl<K, V> IndexMut<usize> for Slice<K, V> { |
469 | fn index_mut(&mut self, index: usize) -> &mut V { |
470 | &mut self.entries[index].value |
471 | } |
472 | } |
473 | |
474 | // We can't have `impl<I: RangeBounds<usize>> Index<I>` because that conflicts |
475 | // both upstream with `Index<usize>` and downstream with `Index<&Q>`. |
476 | // Instead, we repeat the implementations for all the core range types. |
477 | macro_rules! impl_index { |
478 | ($($range:ty),*) => {$( |
479 | impl<K, V, S> Index<$range> for IndexMap<K, V, S> { |
480 | type Output = Slice<K, V>; |
481 | |
482 | fn index(&self, range: $range) -> &Self::Output { |
483 | Slice::from_slice(&self.as_entries()[range]) |
484 | } |
485 | } |
486 | |
487 | impl<K, V, S> IndexMut<$range> for IndexMap<K, V, S> { |
488 | fn index_mut(&mut self, range: $range) -> &mut Self::Output { |
489 | Slice::from_mut_slice(&mut self.as_entries_mut()[range]) |
490 | } |
491 | } |
492 | |
493 | impl<K, V> Index<$range> for Slice<K, V> { |
494 | type Output = Slice<K, V>; |
495 | |
496 | fn index(&self, range: $range) -> &Self { |
497 | Self::from_slice(&self.entries[range]) |
498 | } |
499 | } |
500 | |
501 | impl<K, V> IndexMut<$range> for Slice<K, V> { |
502 | fn index_mut(&mut self, range: $range) -> &mut Self { |
503 | Self::from_mut_slice(&mut self.entries[range]) |
504 | } |
505 | } |
506 | )*} |
507 | } |
508 | impl_index!( |
509 | ops::Range<usize>, |
510 | ops::RangeFrom<usize>, |
511 | ops::RangeFull, |
512 | ops::RangeInclusive<usize>, |
513 | ops::RangeTo<usize>, |
514 | ops::RangeToInclusive<usize>, |
515 | (Bound<usize>, Bound<usize>) |
516 | ); |
517 | |
518 | #[cfg (test)] |
519 | mod tests { |
520 | use super::*; |
521 | |
522 | #[test ] |
523 | fn slice_index() { |
524 | fn check( |
525 | vec_slice: &[(i32, i32)], |
526 | map_slice: &Slice<i32, i32>, |
527 | sub_slice: &Slice<i32, i32>, |
528 | ) { |
529 | assert_eq!(map_slice as *const _, sub_slice as *const _); |
530 | itertools::assert_equal( |
531 | vec_slice.iter().copied(), |
532 | map_slice.iter().map(|(&k, &v)| (k, v)), |
533 | ); |
534 | itertools::assert_equal(vec_slice.iter().map(|(k, _)| k), map_slice.keys()); |
535 | itertools::assert_equal(vec_slice.iter().map(|(_, v)| v), map_slice.values()); |
536 | } |
537 | |
538 | let vec: Vec<(i32, i32)> = (0..10).map(|i| (i, i * i)).collect(); |
539 | let map: IndexMap<i32, i32> = vec.iter().cloned().collect(); |
540 | let slice = map.as_slice(); |
541 | |
542 | // RangeFull |
543 | check(&vec[..], &map[..], &slice[..]); |
544 | |
545 | for i in 0usize..10 { |
546 | // Index |
547 | assert_eq!(vec[i].1, map[i]); |
548 | assert_eq!(vec[i].1, slice[i]); |
549 | assert_eq!(map[&(i as i32)], map[i]); |
550 | assert_eq!(map[&(i as i32)], slice[i]); |
551 | |
552 | // RangeFrom |
553 | check(&vec[i..], &map[i..], &slice[i..]); |
554 | |
555 | // RangeTo |
556 | check(&vec[..i], &map[..i], &slice[..i]); |
557 | |
558 | // RangeToInclusive |
559 | check(&vec[..=i], &map[..=i], &slice[..=i]); |
560 | |
561 | // (Bound<usize>, Bound<usize>) |
562 | let bounds = (Bound::Excluded(i), Bound::Unbounded); |
563 | check(&vec[i + 1..], &map[bounds], &slice[bounds]); |
564 | |
565 | for j in i..=10 { |
566 | // Range |
567 | check(&vec[i..j], &map[i..j], &slice[i..j]); |
568 | } |
569 | |
570 | for j in i..10 { |
571 | // RangeInclusive |
572 | check(&vec[i..=j], &map[i..=j], &slice[i..=j]); |
573 | } |
574 | } |
575 | } |
576 | |
577 | #[test ] |
578 | fn slice_index_mut() { |
579 | fn check_mut( |
580 | vec_slice: &[(i32, i32)], |
581 | map_slice: &mut Slice<i32, i32>, |
582 | sub_slice: &mut Slice<i32, i32>, |
583 | ) { |
584 | assert_eq!(map_slice, sub_slice); |
585 | itertools::assert_equal( |
586 | vec_slice.iter().copied(), |
587 | map_slice.iter_mut().map(|(&k, &mut v)| (k, v)), |
588 | ); |
589 | itertools::assert_equal( |
590 | vec_slice.iter().map(|&(_, v)| v), |
591 | map_slice.values_mut().map(|&mut v| v), |
592 | ); |
593 | } |
594 | |
595 | let vec: Vec<(i32, i32)> = (0..10).map(|i| (i, i * i)).collect(); |
596 | let mut map: IndexMap<i32, i32> = vec.iter().cloned().collect(); |
597 | let mut map2 = map.clone(); |
598 | let slice = map2.as_mut_slice(); |
599 | |
600 | // RangeFull |
601 | check_mut(&vec[..], &mut map[..], &mut slice[..]); |
602 | |
603 | for i in 0usize..10 { |
604 | // IndexMut |
605 | assert_eq!(&mut map[i], &mut slice[i]); |
606 | |
607 | // RangeFrom |
608 | check_mut(&vec[i..], &mut map[i..], &mut slice[i..]); |
609 | |
610 | // RangeTo |
611 | check_mut(&vec[..i], &mut map[..i], &mut slice[..i]); |
612 | |
613 | // RangeToInclusive |
614 | check_mut(&vec[..=i], &mut map[..=i], &mut slice[..=i]); |
615 | |
616 | // (Bound<usize>, Bound<usize>) |
617 | let bounds = (Bound::Excluded(i), Bound::Unbounded); |
618 | check_mut(&vec[i + 1..], &mut map[bounds], &mut slice[bounds]); |
619 | |
620 | for j in i..=10 { |
621 | // Range |
622 | check_mut(&vec[i..j], &mut map[i..j], &mut slice[i..j]); |
623 | } |
624 | |
625 | for j in i..10 { |
626 | // RangeInclusive |
627 | check_mut(&vec[i..=j], &mut map[i..=j], &mut slice[i..=j]); |
628 | } |
629 | } |
630 | } |
631 | } |
632 | |