@@ -34,6 +34,7 @@ pub trait IteratorUtil<A> {
34
34
// FIXME: #5898: should be called map
35
35
fn transform < ' r , B > ( self , f : & ' r fn ( A ) -> B ) -> MapIterator < ' r , A , B , Self > ;
36
36
fn filter < ' r > ( self , predicate : & ' r fn ( & A ) -> bool ) -> FilterIterator < ' r , A , Self > ;
37
+ fn filter_map < ' r , B > ( self , f : & ' r fn ( A ) -> Option < B > ) -> FilterMapIterator < ' r , A , B , Self > ;
37
38
fn enumerate ( self ) -> EnumerateIterator < Self > ;
38
39
fn skip_while < ' r > ( self , predicate : & ' r fn ( & A ) -> bool ) -> SkipWhileIterator < ' r , A , Self > ;
39
40
fn take_while < ' r > ( self , predicate : & ' r fn ( & A ) -> bool ) -> TakeWhileIterator < ' r , A , Self > ;
@@ -74,6 +75,11 @@ impl<A, T: Iterator<A>> IteratorUtil<A> for T {
74
75
FilterIterator { iter : self , predicate : predicate}
75
76
}
76
77
78
+ #[ inline( always) ]
79
+ fn filter_map < ' r , B > ( self , f : & ' r fn ( A ) -> Option < B > ) -> FilterMapIterator < ' r , A , B , T > {
80
+ FilterMapIterator { iter : self , f : f }
81
+ }
82
+
77
83
#[ inline( always) ]
78
84
fn enumerate ( self ) -> EnumerateIterator < T > {
79
85
EnumerateIterator { iter : self , count : 0 }
@@ -213,6 +219,28 @@ impl<'self, A, T: Iterator<A>> Iterator<A> for FilterIterator<'self, A, T> {
213
219
}
214
220
}
215
221
222
+ pub struct FilterMapIterator < ' self , A , B , T > {
223
+ priv iter : T ,
224
+ priv f: & ' self fn ( A ) -> Option < B >
225
+ }
226
+
227
+ impl < ' self , A , B , T : Iterator < A > > Iterator < B > for FilterMapIterator < ' self , A , B , T > {
228
+ #[ inline]
229
+ fn next ( & mut self ) -> Option < B > {
230
+ loop {
231
+ match self . iter . next ( ) {
232
+ None => { return None ; }
233
+ Some ( a) => {
234
+ match ( self . f ) ( a) {
235
+ Some ( b) => { return Some ( b) ; }
236
+ None => { loop ; }
237
+ }
238
+ }
239
+ }
240
+ }
241
+ }
242
+ }
243
+
216
244
pub struct EnumerateIterator < T > {
217
245
priv iter : T ,
218
246
priv count : uint
@@ -432,6 +460,13 @@ mod tests {
432
460
assert_eq ! ( i, expected. len( ) ) ;
433
461
}
434
462
463
+ #[ test]
464
+ fn test_filter_map ( ) {
465
+ let it = Counter :: new ( 0 u, 1 u) . take ( 10 )
466
+ . filter_map ( |x : uint | if x. is_even ( ) { Some ( x* x) } else { None } ) ;
467
+ assert_eq ! ( it. to_vec( ) , ~[ 0 * 0 , 2 * 2 , 4 * 4 , 6 * 6 , 8 * 8 ] ) ;
468
+ }
469
+
435
470
#[ test]
436
471
fn test_iterator_enumerate ( ) {
437
472
let xs = [ 0 u, 1 , 2 , 3 , 4 , 5 ] ;
0 commit comments