diff --git a/src/lib.rs b/src/lib.rs index 925b68e..7851304 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -158,7 +158,7 @@ use num_traits::{One, Zero}; use std::borrow::Borrow; -use std::collections::{hash_map::Iter, HashMap}; +use std::collections::HashMap; use std::hash::Hash; use std::iter; use std::ops::{Add, AddAssign, BitAnd, BitOr, Deref, DerefMut, Index, IndexMut, Sub, SubAssign}; @@ -543,16 +543,77 @@ where impl<'a, T, N> IntoIterator for &'a Counter where T: Hash + Eq, - N: PartialOrd + AddAssign + SubAssign + Zero + One, { type Item = (&'a T, &'a N); - type IntoIter = Iter<'a, T, N>; + type IntoIter = std::collections::hash_map::Iter<'a, T, N>; - fn into_iter(self) -> Iter<'a, T, N> { + fn into_iter(self) -> Self::IntoIter { self.map.iter() } } +impl IntoIterator for Counter +where + T: Hash + Eq, +{ + type Item = (T, N); + type IntoIter = std::collections::hash_map::IntoIter; + + /// Consumes the Counter to produce an iterator that owns the values it returns + /// + /// # Examples + /// ```rust + /// # use counter::Counter; + /// + /// let counter: Counter<_> = "aaab".chars().collect(); + /// + /// let vec: Vec<_> = counter.into_iter().collect(); + /// + /// for (item, count) in &vec { + /// if item == &'a' { + /// assert_eq!(count, &3); + /// } + /// if item == &'b' { + /// assert_eq!(count, &1); + /// } + /// } + /// ``` + + fn into_iter(self) -> Self::IntoIter { + self.map.into_iter() + } +} + +impl<'a, T, N> IntoIterator for &'a mut Counter +where + T: Hash + Eq, +{ + type Item = (&'a T, &'a mut N); + type IntoIter = std::collections::hash_map::IterMut<'a, T, N>; + + /// Creates an iterator that provides mutable references to the counts, but keeps the key immutable + /// + /// # Examples + /// ```rust + /// # use counter::Counter; + /// + /// let mut counter: Counter<_> = "aaab".chars().collect(); + /// + /// for (item, count) in &mut counter { + /// if *item == 'a' { + /// // 'a' is so great it counts as 2 + /// *count *= 2; + /// } + /// } + /// + /// assert_eq!(counter[&'a'], 6); + /// assert_eq!(counter[&'b'], 1); + /// ``` + fn into_iter(self) -> Self::IntoIter { + self.map.iter_mut() + } +} + impl Index<&'_ Q> for Counter where T: Hash + Eq + Borrow, @@ -838,8 +899,8 @@ where #[cfg(test)] mod tests { - use maplit::hashmap; use super::*; + use maplit::hashmap; use std::collections::HashMap; #[test]