diff --git a/src/adaptors/map.rs b/src/adaptors/map.rs index cf5e5a00d..a26ece871 100644 --- a/src/adaptors/map.rs +++ b/src/adaptors/map.rs @@ -4,8 +4,8 @@ use std::marker::PhantomData; #[derive(Clone, Debug)] #[must_use = "iterator adaptors are lazy and do nothing unless consumed"] pub struct MapSpecialCase { - iter: I, - f: F, + pub(crate) iter: I, + pub(crate) f: F, } pub trait MapSpecialCaseFn { diff --git a/src/adaptors/mod.rs b/src/adaptors/mod.rs index 84bbf98e0..cf9642bc5 100644 --- a/src/adaptors/mod.rs +++ b/src/adaptors/mod.rs @@ -5,7 +5,7 @@ //! except according to those terms. mod coalesce; -mod map; +pub(crate) mod map; mod multi_product; pub use self::coalesce::*; #[allow(deprecated)] diff --git a/src/grouping_map.rs b/src/grouping_map.rs index f165723cc..47a7c096e 100644 --- a/src/grouping_map.rs +++ b/src/grouping_map.rs @@ -1,45 +1,39 @@ #![cfg(feature = "use_std")] -use crate::MinMaxResult; +use crate::{ + adaptors::map::{MapSpecialCase, MapSpecialCaseFn}, + MinMaxResult, +}; use std::cmp::Ordering; use std::collections::HashMap; -use std::fmt; use std::hash::Hash; use std::iter::Iterator; use std::ops::{Add, Mul}; /// A wrapper to allow for an easy [`into_grouping_map_by`](crate::Itertools::into_grouping_map_by) +pub type MapForGrouping = MapSpecialCase>; + #[derive(Clone)] -pub struct MapForGrouping(I, F); +pub struct GroupingMapFn(F); -impl fmt::Debug for MapForGrouping { - debug_fmt_fields!(MapForGrouping, 0); +impl std::fmt::Debug for GroupingMapFn { + debug_fmt_fields!(GroupingMapFn,); } -impl MapForGrouping { - pub(crate) fn new(iter: I, key_mapper: F) -> Self { - Self(iter, key_mapper) +impl K> MapSpecialCaseFn for GroupingMapFn { + type Out = (K, V); + fn call(&mut self, v: V) -> Self::Out { + ((self.0)(&v), v) } } -#[allow(clippy::missing_trait_methods)] -impl Iterator for MapForGrouping -where - I: Iterator, - K: Hash + Eq, - F: FnMut(&V) -> K, -{ - type Item = (K, V); - fn next(&mut self) -> Option { - self.0.next().map(|val| ((self.1)(&val), val)) - } - - fn fold(self, init: B, f: G) -> B - where - G: FnMut(B, Self::Item) -> B, - { - let mut key_mapper = self.1; - self.0.map(|val| (key_mapper(&val), val)).fold(init, f) +pub(crate) fn new_map_for_grouping K>( + iter: I, + key_mapper: F, +) -> MapForGrouping { + MapSpecialCase { + iter, + f: GroupingMapFn(key_mapper), } } diff --git a/src/lib.rs b/src/lib.rs index 218b3a8b9..b7973248d 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -3194,7 +3194,7 @@ pub trait Itertools: Iterator { K: Hash + Eq, F: FnMut(&V) -> K, { - grouping_map::new(grouping_map::MapForGrouping::new(self, key_mapper)) + grouping_map::new(grouping_map::new_map_for_grouping(self, key_mapper)) } /// Return all minimum elements of an iterator.