1use serde::ser::{Serialize, Serializer};
12use std::borrow::Borrow;
13use std::collections::{HashMap, HashSet};
14use std::hash::Hash;
15use std::slice;
16use std::sync::atomic::{AtomicBool, Ordering};
17
18#[derive(Clone, Debug)]
45pub struct VecMap<K, V> {
46 data: Vec<(K, V)>,
47 deduped: bool,
53}
54
55impl<K, V> Default for VecMap<K, V> {
56 fn default() -> Self {
57 Self {
58 data: Default::default(),
59 deduped: false,
60 }
61 }
62}
63
64#[cfg(any(test, feature = "test-utils"))]
68impl<K: Eq + Hash, V: PartialEq> PartialEq for VecMap<K, V> {
69 fn eq(&self, other: &Self) -> bool {
70 let lhs: HashMap<&K, &V> = self.data.iter().map(|(k, v)| (k, v)).collect();
71 let rhs: HashMap<&K, &V> = other.data.iter().map(|(k, v)| (k, v)).collect();
72 lhs == rhs
73 }
74}
75
76#[cfg(any(test, feature = "test-utils"))]
77impl<K: Eq + Hash, V: Eq> Eq for VecMap<K, V> {}
78
79impl<K, V> VecMap<K, V> {
80 #[must_use]
81 #[inline]
82 pub fn new() -> Self {
83 Self::default()
84 }
85
86 fn dirty(&mut self) {
88 self.deduped = false;
89 }
90
91 #[must_use]
92 #[inline]
93 pub fn with_capacity(capacity: usize) -> Self {
94 VecMap {
95 data: Vec::with_capacity(capacity),
96 deduped: false,
97 }
98 }
99
100 #[inline]
101 pub fn insert(&mut self, key: K, value: V) {
102 self.data.push((key, value));
103 self.dirty();
104 }
105
106 #[inline]
107 pub fn get<Q>(&self, key: &Q) -> Option<&V>
108 where
109 K: Borrow<Q>,
110 Q: ?Sized + PartialEq,
111 {
112 self.data
113 .iter()
114 .rev()
115 .find(|(k, _)| k.borrow() == key)
116 .map(|(_, v)| v)
117 }
118
119 #[inline]
120 pub fn get_mut<Q>(&mut self, key: &Q) -> Option<&mut V>
121 where
122 K: Borrow<Q>,
123 Q: ?Sized + PartialEq,
124 {
125 self.data
126 .iter_mut()
127 .rev()
128 .find(|(k, _)| (*k).borrow() == key)
129 .map(|(_, v)| v)
130 }
131
132 #[inline]
133 pub fn contains_key<Q>(&self, key: &Q) -> bool
134 where
135 K: Borrow<Q>,
136 Q: ?Sized + PartialEq,
137 {
138 self.data.iter().any(|(k, _)| k.borrow() == key)
139 }
140
141 #[inline]
146 pub fn remove_slow<Q>(&mut self, key: &Q)
147 where
148 K: Borrow<Q>,
149 Q: ?Sized + PartialEq,
150 {
151 self.data.retain(|(k, _)| k.borrow() != key);
152 }
153
154 #[inline]
156 pub fn iter(&self) -> slice::Iter<'_, (K, V)> {
157 self.data.iter()
158 }
159
160 #[inline]
162 pub fn iter_mut(&mut self) -> slice::IterMut<'_, (K, V)> {
163 self.dirty();
164 self.data.iter_mut()
165 }
166
167 #[inline]
169 pub fn len(&self) -> usize {
170 self.data.len()
171 }
172
173 #[inline]
174 pub fn is_empty(&self) -> bool {
175 self.data.is_empty()
176 }
177
178 #[inline]
183 pub fn is_deduped(&self) -> bool {
184 self.deduped
185 }
186}
187
188impl<K: Eq + Hash, V> VecMap<K, V> {
189 pub fn as_deduped_map(&self) -> DedupedVecMap<'_, K, V> {
194 if self.deduped {
195 DedupedVecMap::Borrowed(self)
196 } else {
197 DedupedVecMap::Owned(self.data.iter().map(|(k, v)| (k, v)).collect())
198 }
199 }
200
201 #[allow(unused)]
205 pub(crate) fn defensive_dedup(&self) -> DedupedVecMap<'_, K, V> {
206 if !self.is_deduped() {
207 static WARNED: AtomicBool = AtomicBool::new(false);
208 if !WARNED.swap(true, Ordering::Relaxed) {
209 tracing::warn!(
210 "VecMap not deduped before encoding. Performing defensive on-the-fly dedup"
211 );
212 }
213 }
214
215 self.as_deduped_map()
216 }
217
218 pub fn dedup(&mut self) {
222 if self.deduped {
223 return;
224 }
225
226 self.data.reverse();
227
228 let keep: Vec<bool> = {
250 let mut seen = HashSet::with_capacity(self.len());
251 self.data.iter().map(|(k, _)| seen.insert(k)).collect()
252 };
253
254 let mut keep = keep.into_iter();
255 self.data.retain(|_| keep.next().unwrap_or(false));
256
257 self.deduped = true;
258 }
259}
260
261impl<K, V> From<Vec<(K, V)>> for VecMap<K, V> {
262 fn from(data: Vec<(K, V)>) -> Self {
263 Self {
264 data,
265 deduped: false,
266 }
267 }
268}
269
270impl<K, V> From<VecMap<K, V>> for Vec<(K, V)> {
271 fn from(value: VecMap<K, V>) -> Self {
272 value.data
273 }
274}
275
276impl<K, V> FromIterator<(K, V)> for VecMap<K, V> {
277 fn from_iter<I: IntoIterator<Item = (K, V)>>(iter: I) -> Self {
278 Self {
279 data: iter.into_iter().collect(),
280 deduped: false,
281 }
282 }
283}
284
285impl<K, V> IntoIterator for VecMap<K, V> {
286 type Item = (K, V);
287 type IntoIter = std::vec::IntoIter<(K, V)>;
288
289 fn into_iter(self) -> Self::IntoIter {
290 self.data.into_iter()
291 }
292}
293
294impl<'a, K, V> IntoIterator for &'a VecMap<K, V> {
295 type Item = &'a (K, V);
296 type IntoIter = slice::Iter<'a, (K, V)>;
297
298 fn into_iter(self) -> Self::IntoIter {
299 self.data.iter()
300 }
301}
302
303impl<'a, K, V> IntoIterator for &'a mut VecMap<K, V> {
304 type Item = &'a mut (K, V);
305 type IntoIter = slice::IterMut<'a, (K, V)>;
306
307 fn into_iter(self) -> Self::IntoIter {
308 self.dirty();
310 self.data.iter_mut()
311 }
312}
313
314impl<K, V> Extend<(K, V)> for VecMap<K, V> {
315 fn extend<I: IntoIterator<Item = (K, V)>>(&mut self, iter: I) {
316 self.dirty();
317 self.data.extend(iter);
318 }
319}
320
321impl<K: Serialize + Eq + Hash, V: Serialize> Serialize for VecMap<K, V> {
322 fn serialize<S: Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error> {
323 use serde::ser::SerializeMap;
324
325 let deduped = self.as_deduped_map();
326 let mut map_ser = serializer.serialize_map(Some(deduped.len()))?;
327
328 for (k, v) in deduped.iter() {
329 map_ser.serialize_entry(k, v)?;
330 }
331
332 map_ser.end()
333 }
334}
335
336pub enum DedupedVecMap<'a, K, V> {
337 Borrowed(&'a VecMap<K, V>),
338 Owned(HashMap<&'a K, &'a V>),
339}
340
341impl<'a, K, V> DedupedVecMap<'a, K, V> {
342 #[inline]
343 pub fn iter(&self) -> DedupedVecMapIter<'_, 'a, K, V> {
344 match self {
345 DedupedVecMap::Borrowed(vec_map) => DedupedVecMapIter::Borrowed(vec_map.iter()),
346 DedupedVecMap::Owned(map) => DedupedVecMapIter::Owned(map.iter()),
347 }
348 }
349
350 #[inline]
351 pub fn len(&self) -> usize {
352 match self {
353 DedupedVecMap::Borrowed(vec_map) => vec_map.len(),
354 DedupedVecMap::Owned(map) => map.len(),
355 }
356 }
357
358 #[inline]
359 pub fn is_empty(&self) -> bool {
360 match self {
361 DedupedVecMap::Borrowed(vec_map) => vec_map.is_empty(),
362 DedupedVecMap::Owned(map) => map.is_empty(),
363 }
364 }
365}
366
367pub enum DedupedVecMapIter<'b, 'a: 'b, K, V> {
368 Borrowed(slice::Iter<'a, (K, V)>),
369 Owned(std::collections::hash_map::Iter<'b, &'a K, &'a V>),
370}
371
372impl<'b, 'a: 'b, K, V> Iterator for DedupedVecMapIter<'b, 'a, K, V> {
373 type Item = (&'a K, &'a V);
374
375 fn next(&mut self) -> Option<Self::Item> {
376 match self {
377 DedupedVecMapIter::Borrowed(iter) => iter.next().map(|(k, v)| (k, v)),
378 DedupedVecMapIter::Owned(iter) => iter.next().map(|(&k, &v)| (k, v)),
379 }
380 }
381
382 fn size_hint(&self) -> (usize, Option<usize>) {
383 match self {
384 DedupedVecMapIter::Borrowed(iter) => iter.size_hint(),
385 DedupedVecMapIter::Owned(iter) => iter.size_hint(),
386 }
387 }
388}
389
390impl<'b, 'a: 'b, K, V> ExactSizeIterator for DedupedVecMapIter<'b, 'a, K, V> {}
391
392#[cfg(test)]
393mod tests {
394 use super::*;
395
396 #[test]
397 fn get_returns_last_inserted() {
398 let mut m = VecMap::new();
399 m.insert("a", 1);
400 m.insert("a", 2);
401 assert_eq!(m.get("a"), Some(&2));
402 }
403
404 #[test]
405 fn get_mut_returns_last_inserted() {
406 let mut m = VecMap::new();
407 m.insert("a", 1);
408 m.insert("a", 2);
409 *m.get_mut("a").unwrap() = 42;
410 assert_eq!(m.get("a"), Some(&42));
411 assert_eq!(m.iter().next().unwrap().1, 1);
413 }
414
415 #[test]
416 fn remove_removes_all_occurrences() {
417 let mut m = VecMap::new();
418 m.insert("a", 1);
419 m.insert("b", 2);
420 m.insert("a", 3);
421 m.remove_slow("a");
422 assert_eq!(m.get("a"), None);
423 assert!(!m.contains_key("a"));
424 assert_eq!(m.len(), 1);
425 }
426
427 #[test]
428 fn contains_key_works() {
429 let mut m = VecMap::new();
430 assert!(!m.contains_key("x"));
431 m.insert("x", 10);
432 assert!(m.contains_key("x"));
433 }
434
435 #[test]
436 fn from_iterator() {
437 let m: VecMap<&str, i32> = vec![("a", 1), ("b", 2)].into_iter().collect();
438 assert_eq!(m.len(), 2);
439 assert_eq!(m.get("b"), Some(&2));
440 }
441
442 #[test]
443 fn into_iter_consuming() {
444 let mut m = VecMap::new();
445 m.insert("a", 1);
446 m.insert("b", 2);
447 let pairs: Vec<_> = m.into_iter().collect();
448 assert_eq!(pairs, vec![("a", 1), ("b", 2)]);
449 }
450
451 #[test]
452 fn is_deduped_false_initially() {
453 let m: VecMap<&str, i32> = VecMap::new();
454 assert!(!m.is_deduped());
455 }
456
457 #[test]
458 fn is_deduped_false_after_from() {
459 let m: VecMap<&str, i32> = vec![("a", 1)].into();
460 assert!(!m.is_deduped());
461 }
462
463 #[test]
464 fn is_deduped_false_after_collect() {
465 let m: VecMap<&str, i32> = vec![("a", 1)].into_iter().collect();
466 assert!(!m.is_deduped());
467 }
468
469 #[test]
470 fn dedup_sets_flag() {
471 let mut m = VecMap::new();
472 m.insert("a", 1);
473 assert!(!m.is_deduped());
474 m.dedup();
475 assert!(m.is_deduped());
476 }
477
478 #[test]
479 fn dedup_on_empty_map() {
480 let mut m: VecMap<String, i32> = VecMap::new();
481 m.dedup();
482 assert!(m.is_deduped());
483 assert!(m.is_empty());
484 }
485
486 #[test]
487 fn dedup_no_duplicates() {
488 let mut m = VecMap::new();
489 m.insert("a", 1);
490 m.insert("b", 2);
491 m.insert("c", 3);
492 m.dedup();
493 assert_eq!(m.len(), 3);
494 assert_eq!(m.get("a"), Some(&1));
495 assert_eq!(m.get("b"), Some(&2));
496 assert_eq!(m.get("c"), Some(&3));
497 }
498
499 #[test]
500 fn dedup_keeps_last_value() {
501 let mut m = VecMap::new();
502 m.insert("a", 1);
503 m.insert("b", 10);
504 m.insert("a", 2);
505 m.insert("a", 3);
506 m.insert("b", 20);
507 m.dedup();
508 assert_eq!(m.len(), 2);
509 assert_eq!(m.get("a"), Some(&3));
510 assert_eq!(m.get("b"), Some(&20));
511 }
512
513 #[test]
514 fn dedup_is_idempotent() {
515 let mut m = VecMap::new();
516 m.insert("a", 1);
517 m.insert("a", 2);
518 m.dedup();
519 assert!(m.is_deduped());
520 assert_eq!(m.len(), 1);
521 m.dedup();
522 assert!(m.is_deduped());
523 assert_eq!(m.len(), 1);
524 assert_eq!(m.get("a"), Some(&2));
525 }
526
527 #[test]
528 fn insert_dirties_dedup_flag() {
529 let mut m = VecMap::new();
530 m.insert("a", 1);
531 m.dedup();
532 assert!(m.is_deduped());
533
534 m.insert("b", 2);
535 assert!(!m.is_deduped());
536 }
537
538 #[test]
539 fn extend_dirties_dedup_flag() {
540 let mut m = VecMap::new();
541 m.insert("a", 1);
542 m.dedup();
543 assert!(m.is_deduped());
544
545 m.extend(vec![("b", 2)]);
546 assert!(!m.is_deduped());
547 }
548
549 #[test]
550 fn iter_mut_dirties_dedup_flag() {
551 let mut m = VecMap::new();
552 m.insert("a", 1);
553 m.dedup();
554 assert!(m.is_deduped());
555
556 for (_, v) in m.iter_mut() {
557 *v += 1;
558 }
559
560 assert!(!m.is_deduped());
561 }
562
563 #[test]
564 fn deduped_vec_map_borrowed_iter_and_len() {
565 let mut m = VecMap::new();
566 m.insert("a", 1);
567 m.insert("b", 2);
568 m.dedup();
569
570 let d = m.defensive_dedup();
571 assert!(matches!(d, DedupedVecMap::Borrowed(_)));
572 assert_eq!(d.len(), 2);
573
574 let mut items: Vec<_> = d.iter().collect();
575 items.sort_by_key(|(k, _)| **k);
576 assert_eq!(items, vec![(&"a", &1), (&"b", &2)]);
577 }
578
579 #[test]
580 fn deduped_vec_map_copy_iter_and_len() {
581 let mut m = VecMap::new();
582 m.insert("a", 1);
583 m.insert("a", 2);
584 m.insert("b", 3);
585
586 let d = m.defensive_dedup();
587 assert!(matches!(d, DedupedVecMap::Owned(_)));
588 assert_eq!(d.len(), 2);
589
590 let items: HashMap<&&str, &i32> = d.iter().collect();
591 assert_eq!(items[&"a"], &2);
592 assert_eq!(items[&"b"], &3);
593 }
594
595 #[test]
596 fn deduped_vec_map_iter_exact_size() {
597 let mut m = VecMap::new();
598 m.insert("a", 1);
599 m.insert("b", 2);
600 m.insert("c", 3);
601 m.dedup();
602
603 let d = m.defensive_dedup();
604 let mut iter = d.iter();
605 assert_eq!(iter.len(), 3);
606 iter.next();
607 assert_eq!(iter.len(), 2);
608 }
609
610 #[test]
611 fn deduped_vec_map_empty() {
612 let m: VecMap<String, i32> = VecMap::new();
613 let d = DedupedVecMap::Borrowed(&m);
614 assert_eq!(d.len(), 0);
615 assert_eq!(d.iter().count(), 0);
616 }
617
618 #[test]
619 fn dedup_does_not_require_clone() {
620 #[derive(Debug, PartialEq, Eq, Hash)]
621 struct NonCloneKey(u32);
622
623 let mut m = VecMap::new();
624 m.insert(NonCloneKey(1), "a");
625 m.insert(NonCloneKey(2), "b");
626 m.insert(NonCloneKey(1), "c");
627 m.dedup();
628 assert_eq!(m.len(), 2);
629 assert_eq!(m.get(&NonCloneKey(1)), Some(&"c"));
630 assert_eq!(m.get(&NonCloneKey(2)), Some(&"b"));
631 }
632
633 #[test]
634 fn serialize_deduplicates_keeping_last() {
635 let mut m = VecMap::new();
636 m.insert("a", 0);
637 m.insert("b", 0);
638 m.insert("b", 1);
639 m.insert("a", 1);
640 m.insert("a", 3);
641 m.insert("b", 2);
642
643 let serialized: serde_json::Value = serde_json::to_value(&m).unwrap();
644 let obj = serialized.as_object().unwrap();
645
646 assert_eq!(obj.len(), 2);
647 assert_eq!(obj.get("a").unwrap(), 3);
648 assert_eq!(obj.get("b").unwrap(), 2);
649 }
650}