1use std::{
2 borrow::Borrow,
3 collections::{BTreeMap, HashMap},
4 fmt::{self, Debug},
5 hash::BuildHasher,
6 iter::FusedIterator,
7 marker::PhantomData,
8 ops::{Bound, Index, RangeBounds},
9};
10
11use bincode::{BorrowDecode, Decode, Encode};
12use indexmap::IndexMap;
13use serde::{
14 Deserialize, Serialize,
15 de::{MapAccess, Visitor},
16};
17
18#[derive(Clone, PartialEq, Eq, Hash, PartialOrd, Ord, Encode, Decode)]
46#[rustfmt::skip] #[bincode(
48 decode_bounds = "K: Decode<__Context> + 'static, V: Decode<__Context> + 'static",
49 borrow_decode_bounds = "K: BorrowDecode<'__de, __Context> + '__de, V: BorrowDecode<'__de, __Context> + '__de"
50)]
51pub struct FrozenMap<K, V> {
52 pub(crate) entries: Box<[(K, V)]>,
54}
55
56impl<K: Serialize, V: Serialize> Serialize for FrozenMap<K, V> {
57 fn serialize<S: serde::Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error> {
58 serializer.collect_map(self.iter())
59 }
60}
61
62impl<'de, K, V> Deserialize<'de> for FrozenMap<K, V>
63where
64 K: Deserialize<'de> + Ord,
65 V: Deserialize<'de>,
66{
67 fn deserialize<D: serde::Deserializer<'de>>(deserializer: D) -> Result<Self, D::Error> {
68 struct MapVisitor<K, V>(PhantomData<(K, V)>);
69
70 impl<'de, K, V> Visitor<'de> for MapVisitor<K, V>
71 where
72 K: Deserialize<'de> + Ord,
73 V: Deserialize<'de>,
74 {
75 type Value = FrozenMap<K, V>;
76
77 fn expecting(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result {
78 formatter.write_str("a map")
79 }
80
81 fn visit_map<A: MapAccess<'de>>(self, mut map: A) -> Result<Self::Value, A::Error> {
82 let mut entries = Vec::with_capacity(map.size_hint().unwrap_or(0));
83 while let Some(entry) = map.next_entry()? {
84 entries.push(entry);
85 }
86 Ok(FrozenMap::from(entries))
87 }
88 }
89
90 deserializer.deserialize_map(MapVisitor(PhantomData))
91 }
92}
93
94impl<K, V> FrozenMap<K, V> {
95 pub fn new() -> Self {
97 FrozenMap {
98 entries: Box::from([]),
102 }
103 }
104}
105
106impl<K, V> FrozenMap<K, V>
107where
108 K: Ord,
109{
110 pub fn from_unique_sorted_box(entries: Box<[(K, V)]>) -> Self {
114 assert_unique_sorted(&entries);
115 FrozenMap { entries }
116 }
117
118 pub fn from_unique_sorted_box_unchecked(entries: Box<[(K, V)]>) -> Self {
132 debug_assert_unique_sorted(&entries);
133 FrozenMap { entries }
134 }
135
136 pub(crate) fn from_unique_box_inner(mut entries: Box<[(K, V)]>) -> Self {
140 entries.sort_unstable_by(|a, b| a.0.cmp(&b.0));
141 Self::from_unique_sorted_box_unchecked(entries)
142 }
143
144 pub(crate) fn from_vec_inner(mut entries: Vec<(K, V)>) -> Self {
148 entries.sort_by(|a, b| a.0.cmp(&b.0));
150 entries.dedup_by(|later, earlier| {
154 if later.0 == earlier.0 {
155 std::mem::swap(later, earlier);
156 true
157 } else {
158 false
159 }
160 });
161 Self::from_unique_sorted_box_unchecked(entries.into_boxed_slice())
162 }
163}
164
165#[track_caller]
166fn assert_unique_sorted<K: Ord, V>(entries: &[(K, V)]) {
167 assert!(
168 entries.is_sorted_by(|a, b| a.0 < b.0),
169 "FrozenMap entries must be unique and sorted",
170 )
171}
172
173#[track_caller]
174fn debug_assert_unique_sorted<K: Ord, V>(entries: &[(K, V)]) {
175 debug_assert!(
176 entries.is_sorted_by(|a, b| a.0 < b.0),
177 "FrozenMap entries must be unique and sorted",
178 )
179}
180
181impl<K: Ord, V> FromIterator<(K, V)> for FrozenMap<K, V> {
182 fn from_iter<T: IntoIterator<Item = (K, V)>>(entries: T) -> Self {
186 let entries: Vec<_> = entries.into_iter().collect();
187 Self::from(entries)
188 }
189}
190
191impl<K, V> From<BTreeMap<K, V>> for FrozenMap<K, V> {
192 fn from(map: BTreeMap<K, V>) -> Self {
197 if map.is_empty() {
198 return Self::new();
199 }
200 FrozenMap {
201 entries: map.into_iter().collect(),
202 }
203 }
204}
205
206impl<K, V, S> From<HashMap<K, V, S>> for FrozenMap<K, V>
207where
208 K: Ord,
209 S: BuildHasher,
210{
211 fn from(map: HashMap<K, V, S>) -> Self {
215 if map.is_empty() {
216 return Self::new();
217 }
218 Self::from_unique_box_inner(map.into_iter().collect())
219 }
220}
221
222impl<K, V, S> From<IndexMap<K, V, S>> for FrozenMap<K, V>
223where
224 K: Ord,
225 S: BuildHasher,
226{
227 fn from(map: IndexMap<K, V, S>) -> Self {
231 if map.is_empty() {
232 return Self::new();
233 }
234 Self::from_unique_box_inner(map.into_iter().collect())
235 }
236}
237
238impl<K: Ord, V> From<Vec<(K, V)>> for FrozenMap<K, V> {
239 fn from(entries: Vec<(K, V)>) -> Self {
243 if entries.is_empty() {
244 return Self::new();
245 }
246 Self::from_vec_inner(entries)
247 }
248}
249
250impl<K: Ord, V> From<Box<[(K, V)]>> for FrozenMap<K, V> {
251 fn from(entries: Box<[(K, V)]>) -> Self {
255 if entries.is_empty() {
256 return Self::new();
257 }
258 Self::from_vec_inner(Vec::from(entries))
259 }
260}
261
262impl<K, V> From<&[(K, V)]> for FrozenMap<K, V>
263where
264 K: Ord + Clone,
265 V: Clone,
266{
267 fn from(entries: &[(K, V)]) -> Self {
271 if entries.is_empty() {
272 return Self::new();
273 }
274 Self::from_vec_inner(Vec::from(entries))
275 }
276}
277
278impl<K: Ord, V, const N: usize> From<[(K, V); N]> for FrozenMap<K, V> {
279 fn from(entries: [(K, V); N]) -> Self {
283 if entries.is_empty() {
284 return Self::new();
285 }
286 Self::from_vec_inner(Vec::from(entries))
287 }
288}
289
290impl<K, V> FrozenMap<K, V> {
291 pub const fn len(&self) -> usize {
293 self.entries.len()
294 }
295
296 pub const fn is_empty(&self) -> bool {
298 self.entries.is_empty()
299 }
300
301 pub const fn as_slice(&self) -> &[(K, V)] {
303 &self.entries
304 }
305
306 pub fn get<Q>(&self, key: &Q) -> Option<&V>
308 where
309 K: Borrow<Q> + Ord,
310 Q: Ord + ?Sized,
311 {
312 self.get_key_value(key).map(|(_, v)| v)
313 }
314
315 pub fn get_key_value<Q>(&self, key: &Q) -> Option<(&K, &V)>
317 where
318 K: Borrow<Q> + Ord,
319 Q: Ord + ?Sized,
320 {
321 let idx = self
322 .entries
323 .binary_search_by(|(k, _)| k.borrow().cmp(key))
324 .ok()?;
325 let (k, v) = &self.entries[idx];
326 Some((k, v))
327 }
328
329 pub fn contains_key<Q>(&self, key: &Q) -> bool
331 where
332 K: Borrow<Q> + Ord,
333 Q: Ord + ?Sized,
334 {
335 self.entries
336 .binary_search_by(|(k, _)| k.borrow().cmp(key))
337 .is_ok()
338 }
339
340 pub fn first_key_value(&self) -> Option<(&K, &V)> {
342 self.entries.first().map(|(k, v)| (k, v))
343 }
344
345 pub fn last_key_value(&self) -> Option<(&K, &V)> {
347 self.entries.last().map(|(k, v)| (k, v))
348 }
349
350 pub fn iter(&self) -> Iter<'_, K, V> {
352 Iter {
353 inner: self.entries.iter(),
354 }
355 }
356
357 pub fn keys(&self) -> Keys<'_, K, V> {
359 Keys { inner: self.iter() }
360 }
361
362 pub fn values(&self) -> Values<'_, K, V> {
364 Values { inner: self.iter() }
365 }
366
367 pub fn into_keys(self) -> IntoKeys<K, V> {
369 IntoKeys {
370 inner: self.into_iter(),
371 }
372 }
373
374 pub fn into_values(self) -> IntoValues<K, V> {
376 IntoValues {
377 inner: self.into_iter(),
378 }
379 }
380
381 pub fn range<T, R>(&self, range: R) -> Range<'_, K, V>
383 where
384 T: Ord + ?Sized,
385 K: Borrow<T> + Ord,
386 R: RangeBounds<T>,
387 {
388 let start = match range.start_bound() {
389 Bound::Included(key) => self
390 .entries
391 .binary_search_by(|(k, _)| k.borrow().cmp(key))
392 .unwrap_or_else(|i| i),
393 Bound::Excluded(key) => {
394 match self.entries.binary_search_by(|(k, _)| k.borrow().cmp(key)) {
395 Ok(i) => i + 1,
396 Err(i) => i,
397 }
398 }
399 Bound::Unbounded => 0,
400 };
401
402 let end = match range.end_bound() {
403 Bound::Included(key) => {
404 match self.entries.binary_search_by(|(k, _)| k.borrow().cmp(key)) {
405 Ok(i) => i + 1,
406 Err(i) => i,
407 }
408 }
409 Bound::Excluded(key) => self
410 .entries
411 .binary_search_by(|(k, _)| k.borrow().cmp(key))
412 .unwrap_or_else(|i| i),
413 Bound::Unbounded => self.entries.len(),
414 };
415
416 let slice = if start <= end && end <= self.entries.len() {
417 &self.entries[start..end]
418 } else {
419 &[]
420 };
421
422 Range {
423 inner: slice.iter(),
424 }
425 }
426
427 #[must_use]
430 pub fn extend(&self, entries: impl IntoIterator<Item = (K, V)>) -> Self
431 where
432 K: Clone + Ord,
433 V: Clone,
434 {
435 self.as_slice().iter().cloned().chain(entries).collect()
436 }
437}
438
439impl<K, V> Default for FrozenMap<K, V> {
441 fn default() -> Self {
442 Self::new()
443 }
444}
445
446impl<K: Debug, V: Debug> Debug for FrozenMap<K, V> {
447 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
448 f.debug_map().entries(self.iter()).finish()
449 }
450}
451
452impl<K, Q: ?Sized, V> Index<&Q> for FrozenMap<K, V>
453where
454 K: Borrow<Q> + Ord,
455 Q: Ord,
456{
457 type Output = V;
458
459 fn index(&self, key: &Q) -> &V {
460 self.get(key).expect("no entry found for key")
461 }
462}
463
464impl<K, V> AsRef<[(K, V)]> for FrozenMap<K, V> {
465 fn as_ref(&self) -> &[(K, V)] {
466 self.as_slice()
467 }
468}
469
470impl<K, V> From<FrozenMap<K, V>> for Box<[(K, V)]> {
471 fn from(map: FrozenMap<K, V>) -> Self {
472 map.entries
473 }
474}
475
476impl<'a, K, V> IntoIterator for &'a FrozenMap<K, V> {
477 type Item = (&'a K, &'a V);
478 type IntoIter = Iter<'a, K, V>;
479
480 fn into_iter(self) -> Iter<'a, K, V> {
481 self.iter()
482 }
483}
484
485impl<K, V> IntoIterator for FrozenMap<K, V> {
486 type Item = (K, V);
487 type IntoIter = IntoIter<K, V>;
488
489 fn into_iter(self) -> IntoIter<K, V> {
490 IntoIter {
491 inner: self.entries.into_vec().into_iter(),
492 }
493 }
494}
495
496pub struct Iter<'a, K, V> {
498 inner: std::slice::Iter<'a, (K, V)>,
499}
500
501impl<K: Debug, V: Debug> Debug for Iter<'_, K, V> {
502 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
503 f.debug_list()
504 .entries(self.inner.clone().map(|(k, v)| (k, v)))
505 .finish()
506 }
507}
508
509impl<'a, K, V> Iterator for Iter<'a, K, V> {
510 type Item = (&'a K, &'a V);
511
512 fn next(&mut self) -> Option<Self::Item> {
513 self.inner.next().map(|(k, v)| (k, v))
514 }
515
516 fn size_hint(&self) -> (usize, Option<usize>) {
517 self.inner.size_hint()
518 }
519
520 fn last(mut self) -> Option<Self::Item> {
521 self.next_back()
522 }
523
524 fn nth(&mut self, n: usize) -> Option<Self::Item> {
525 self.inner.nth(n).map(|(k, v)| (k, v))
526 }
527
528 fn count(self) -> usize {
529 self.inner.len()
530 }
531}
532
533impl<K, V> DoubleEndedIterator for Iter<'_, K, V> {
534 fn next_back(&mut self) -> Option<Self::Item> {
535 self.inner.next_back().map(|(k, v)| (k, v))
536 }
537
538 fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
539 self.inner.nth_back(n).map(|(k, v)| (k, v))
540 }
541}
542
543impl<K, V> ExactSizeIterator for Iter<'_, K, V> {
544 fn len(&self) -> usize {
545 self.inner.len()
546 }
547}
548
549impl<K, V> FusedIterator for Iter<'_, K, V> {}
550
551impl<K, V> Clone for Iter<'_, K, V> {
553 fn clone(&self) -> Self {
554 Self {
555 inner: self.inner.clone(),
556 }
557 }
558}
559
560pub struct IntoIter<K, V> {
562 inner: std::vec::IntoIter<(K, V)>,
563}
564
565impl<K: Debug, V: Debug> Debug for IntoIter<K, V> {
566 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
567 f.debug_list().entries(self.inner.as_slice()).finish()
568 }
569}
570
571impl<K, V> Iterator for IntoIter<K, V> {
572 type Item = (K, V);
573
574 fn next(&mut self) -> Option<Self::Item> {
575 self.inner.next()
576 }
577
578 fn size_hint(&self) -> (usize, Option<usize>) {
579 self.inner.size_hint()
580 }
581
582 fn count(self) -> usize {
583 self.inner.len()
584 }
585}
586
587impl<K, V> DoubleEndedIterator for IntoIter<K, V> {
588 fn next_back(&mut self) -> Option<Self::Item> {
589 self.inner.next_back()
590 }
591}
592
593impl<K, V> ExactSizeIterator for IntoIter<K, V> {
594 fn len(&self) -> usize {
595 self.inner.len()
596 }
597}
598
599impl<K, V> FusedIterator for IntoIter<K, V> {}
600
601pub struct Keys<'a, K, V> {
603 inner: Iter<'a, K, V>,
604}
605
606impl<K: Debug, V> Debug for Keys<'_, K, V> {
607 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
608 f.debug_list()
609 .entries(self.inner.inner.clone().map(|(k, _)| k))
610 .finish()
611 }
612}
613
614impl<'a, K, V> Iterator for Keys<'a, K, V> {
615 type Item = &'a K;
616
617 fn next(&mut self) -> Option<Self::Item> {
618 self.inner.next().map(|(k, _)| k)
619 }
620
621 fn size_hint(&self) -> (usize, Option<usize>) {
622 self.inner.size_hint()
623 }
624
625 fn last(mut self) -> Option<Self::Item> {
626 self.next_back()
627 }
628
629 fn count(self) -> usize {
630 self.inner.len()
631 }
632}
633
634impl<K, V> DoubleEndedIterator for Keys<'_, K, V> {
635 fn next_back(&mut self) -> Option<Self::Item> {
636 self.inner.next_back().map(|(k, _)| k)
637 }
638}
639
640impl<K, V> ExactSizeIterator for Keys<'_, K, V> {
641 fn len(&self) -> usize {
642 self.inner.len()
643 }
644}
645
646impl<K, V> FusedIterator for Keys<'_, K, V> {}
647
648impl<K, V> Clone for Keys<'_, K, V> {
650 fn clone(&self) -> Self {
651 Self {
652 inner: self.inner.clone(),
653 }
654 }
655}
656
657pub struct Values<'a, K, V> {
659 inner: Iter<'a, K, V>,
660}
661
662impl<K, V: Debug> Debug for Values<'_, K, V> {
663 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
664 f.debug_list()
665 .entries(self.inner.inner.clone().map(|(_, v)| v))
666 .finish()
667 }
668}
669
670impl<'a, K, V> Iterator for Values<'a, K, V> {
671 type Item = &'a V;
672
673 fn next(&mut self) -> Option<Self::Item> {
674 self.inner.next().map(|(_, v)| v)
675 }
676
677 fn size_hint(&self) -> (usize, Option<usize>) {
678 self.inner.size_hint()
679 }
680
681 fn last(mut self) -> Option<Self::Item> {
682 self.next_back()
683 }
684
685 fn count(self) -> usize {
686 self.inner.len()
687 }
688}
689
690impl<K, V> DoubleEndedIterator for Values<'_, K, V> {
691 fn next_back(&mut self) -> Option<Self::Item> {
692 self.inner.next_back().map(|(_, v)| v)
693 }
694}
695
696impl<K, V> ExactSizeIterator for Values<'_, K, V> {
697 fn len(&self) -> usize {
698 self.inner.len()
699 }
700}
701
702impl<K, V> FusedIterator for Values<'_, K, V> {}
703
704impl<K, V> Clone for Values<'_, K, V> {
706 fn clone(&self) -> Self {
707 Self {
708 inner: self.inner.clone(),
709 }
710 }
711}
712
713pub struct IntoKeys<K, V> {
715 inner: IntoIter<K, V>,
716}
717
718impl<K: Debug, V> Debug for IntoKeys<K, V> {
719 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
720 f.debug_list()
721 .entries(self.inner.inner.as_slice().iter().map(|(k, _)| k))
722 .finish()
723 }
724}
725
726impl<K, V> Iterator for IntoKeys<K, V> {
727 type Item = K;
728
729 fn next(&mut self) -> Option<Self::Item> {
730 self.inner.next().map(|(k, _)| k)
731 }
732
733 fn size_hint(&self) -> (usize, Option<usize>) {
734 self.inner.size_hint()
735 }
736
737 fn count(self) -> usize {
738 self.inner.len()
739 }
740}
741
742impl<K, V> DoubleEndedIterator for IntoKeys<K, V> {
743 fn next_back(&mut self) -> Option<Self::Item> {
744 self.inner.next_back().map(|(k, _)| k)
745 }
746}
747
748impl<K, V> ExactSizeIterator for IntoKeys<K, V> {
749 fn len(&self) -> usize {
750 self.inner.len()
751 }
752}
753
754impl<K, V> FusedIterator for IntoKeys<K, V> {}
755
756pub struct IntoValues<K, V> {
758 inner: IntoIter<K, V>,
759}
760
761impl<K, V: Debug> Debug for IntoValues<K, V> {
762 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
763 f.debug_list()
764 .entries(self.inner.inner.as_slice().iter().map(|(_, v)| v))
765 .finish()
766 }
767}
768
769impl<K, V> Iterator for IntoValues<K, V> {
770 type Item = V;
771
772 fn next(&mut self) -> Option<Self::Item> {
773 self.inner.next().map(|(_, v)| v)
774 }
775
776 fn size_hint(&self) -> (usize, Option<usize>) {
777 self.inner.size_hint()
778 }
779
780 fn count(self) -> usize {
781 self.inner.len()
782 }
783}
784
785impl<K, V> DoubleEndedIterator for IntoValues<K, V> {
786 fn next_back(&mut self) -> Option<Self::Item> {
787 self.inner.next_back().map(|(_, v)| v)
788 }
789}
790
791impl<K, V> ExactSizeIterator for IntoValues<K, V> {
792 fn len(&self) -> usize {
793 self.inner.len()
794 }
795}
796
797impl<K, V> FusedIterator for IntoValues<K, V> {}
798
799pub struct Range<'a, K, V> {
801 inner: std::slice::Iter<'a, (K, V)>,
802}
803
804impl<K: Debug, V: Debug> Debug for Range<'_, K, V> {
805 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
806 f.debug_list().entries(self.clone()).finish()
807 }
808}
809
810impl<'a, K, V> Iterator for Range<'a, K, V> {
811 type Item = (&'a K, &'a V);
812
813 fn next(&mut self) -> Option<Self::Item> {
814 self.inner.next().map(|(k, v)| (k, v))
815 }
816
817 fn size_hint(&self) -> (usize, Option<usize>) {
818 self.inner.size_hint()
819 }
820
821 fn last(mut self) -> Option<Self::Item> {
822 self.next_back()
823 }
824
825 fn count(self) -> usize {
826 self.inner.len()
827 }
828}
829
830impl<K, V> DoubleEndedIterator for Range<'_, K, V> {
831 fn next_back(&mut self) -> Option<Self::Item> {
832 self.inner.next_back().map(|(k, v)| (k, v))
833 }
834}
835
836impl<K, V> ExactSizeIterator for Range<'_, K, V> {
837 fn len(&self) -> usize {
838 self.inner.len()
839 }
840}
841
842impl<K, V> FusedIterator for Range<'_, K, V> {}
843
844impl<K, V> Clone for Range<'_, K, V> {
846 fn clone(&self) -> Self {
847 Self {
848 inner: self.inner.clone(),
849 }
850 }
851}
852
853#[cfg(test)]
854mod tests {
855 use super::*;
856
857 #[test]
858 fn serde_uses_map_shape() {
859 let map = FrozenMap::from([("b", 2), ("a", 1)]);
860 let json = serde_json::to_string(&map).unwrap();
861
862 assert_eq!(json, r#"{"a":1,"b":2}"#);
863 assert_eq!(
864 serde_json::from_str::<FrozenMap<&str, i32>>(r#"{"b":2, "a":1}"#).unwrap(),
865 map
866 );
867 }
868
869 #[test]
870 fn test_empty() {
871 let map = FrozenMap::<i32, i32>::new();
872 assert!(map.is_empty());
873 assert_eq!(map.len(), 0);
874 assert_eq!(map.get(&1), None);
875 }
876
877 #[test]
878 fn test_from_btreemap() {
879 let mut btree = BTreeMap::new();
880 btree.insert(3, "c");
881 btree.insert(1, "a");
882 btree.insert(2, "b");
883
884 let frozen = FrozenMap::from(btree);
885 assert_eq!(frozen.len(), 3);
886 assert_eq!(frozen.get(&1), Some(&"a"));
887 assert_eq!(frozen.get(&2), Some(&"b"));
888 assert_eq!(frozen.get(&3), Some(&"c"));
889
890 let keys: Vec<_> = frozen.keys().copied().collect();
891 assert_eq!(keys, vec![1, 2, 3]);
892 }
893
894 #[test]
895 fn test_from_overlapping_vec() {
896 let frozen = FrozenMap::from(vec![(1, "a"), (1, "b"), (2, "c")]);
897 assert_eq!(frozen.len(), 2);
898 assert_eq!(frozen.get(&1), Some(&"b"));
900 assert_eq!(frozen.get(&2), Some(&"c"));
901 }
902
903 #[test]
904 fn test_range() {
905 let frozen = FrozenMap::from([(1, "a"), (2, "b"), (3, "c"), (4, "d"), (5, "e")]);
906
907 let range: Vec<_> = frozen.range(2..4).collect();
908 assert_eq!(range, vec![(&2, &"b"), (&3, &"c")]);
909
910 let range: Vec<_> = frozen.range(2..=4).collect();
911 assert_eq!(range, vec![(&2, &"b"), (&3, &"c"), (&4, &"d")]);
912
913 let range: Vec<_> = frozen.range(..3).collect();
914 assert_eq!(range, vec![(&1, &"a"), (&2, &"b")]);
915 }
916
917 #[test]
918 fn test_index() {
919 let frozen = FrozenMap::from([(1, "a"), (2, "b")]);
920 assert_eq!(frozen[&1], "a");
921 assert_eq!(frozen[&2], "b");
922 }
923
924 #[test]
925 #[should_panic(expected = "no entry found for key")]
926 fn test_index_missing() {
927 let frozen = FrozenMap::from([(1, "a")]);
928 let _ = frozen[&2];
929 }
930
931 #[test]
932 fn test_first_last() {
933 let frozen = FrozenMap::from([(2, "b"), (1, "a"), (3, "c")]);
934 assert_eq!(frozen.first_key_value(), Some((&1, &"a")));
935 assert_eq!(frozen.last_key_value(), Some((&3, &"c")));
936
937 let empty = FrozenMap::<i32, i32>::new();
938 assert_eq!(empty.first_key_value(), None);
939 assert_eq!(empty.last_key_value(), None);
940 }
941
942 #[test]
943 fn test_as_ref() {
944 let frozen = FrozenMap::from([(2, "b"), (1, "a"), (3, "c")]);
945 let slice: &[(i32, &str)] = frozen.as_ref();
946 assert_eq!(slice, &[(1, "a"), (2, "b"), (3, "c")]);
947
948 let empty = FrozenMap::<i32, i32>::new();
949 let empty_slice: &[(i32, i32)] = empty.as_ref();
950 assert_eq!(empty_slice, &[]);
951 }
952
953 #[test]
954 fn test_from_hashmap() {
955 let mut map = HashMap::new();
956 map.insert(3, "c");
957 map.insert(1, "a");
958 map.insert(2, "b");
959
960 let frozen = FrozenMap::from(map);
961 assert_eq!(frozen.len(), 3);
962 assert_eq!(frozen.get(&1), Some(&"a"));
963 let keys: Vec<_> = frozen.keys().copied().collect();
964 assert_eq!(keys, vec![1, 2, 3]);
965 }
966
967 #[test]
968 fn test_from_unique_sorted_box() {
969 let frozen = FrozenMap::from_unique_sorted_box(Box::from([(1, "a"), (2, "b")]));
970 assert_eq!(frozen.len(), 2);
971 assert_eq!(frozen.get(&1), Some(&"a"));
972 assert_eq!(frozen.get(&2), Some(&"b"));
973 }
974
975 #[test]
976 #[should_panic(expected = "FrozenMap entries must be unique and sorted")]
977 fn test_from_unique_sorted_box_panics() {
978 let _ = FrozenMap::from_unique_sorted_box(Box::from([(1, "a"), (1, "b")]));
979 }
980}