Skip to content

Commit e83e568

Browse files
committed
---
yaml --- r: 61435 b: refs/heads/try c: 9ffbe69 h: refs/heads/master i: 61433: dc4a174 61431: 774808c v: v3
1 parent 913a364 commit e83e568

File tree

2 files changed

+36
-1
lines changed

2 files changed

+36
-1
lines changed

[refs]

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
refs/heads/master: 2d28d645422c1617be58c8ca7ad9a457264ca850
33
refs/heads/snap-stage1: e33de59e47c5076a89eadeb38f4934f58a3618a6
44
refs/heads/snap-stage3: 2d28d645422c1617be58c8ca7ad9a457264ca850
5-
refs/heads/try: f7e58ebe84513ed65b1694311f8c4f35e53e8c0e
5+
refs/heads/try: 9ffbe69234317859ca910fe5c419cacf4089d60b
66
refs/tags/release-0.1: 1f5c5126e96c79d22cb7862f75304136e204f105
77
refs/heads/ndm: f3868061cd7988080c30d6d5bf352a5a5fe2460b
88
refs/heads/try2: 147ecfdd8221e4a4d4e090486829a06da1e0ca3c

branches/try/src/libcore/iterator.rs

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ pub trait IteratorUtil<A> {
3434
// FIXME: #5898: should be called map
3535
fn transform<'r, B>(self, f: &'r fn(A) -> B) -> MapIterator<'r, A, B, Self>;
3636
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>;
3738
fn enumerate(self) -> EnumerateIterator<Self>;
3839
fn skip_while<'r>(self, predicate: &'r fn(&A) -> bool) -> SkipWhileIterator<'r, A, Self>;
3940
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 {
7475
FilterIterator{iter: self, predicate: predicate}
7576
}
7677

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+
7783
#[inline(always)]
7884
fn enumerate(self) -> EnumerateIterator<T> {
7985
EnumerateIterator{iter: self, count: 0}
@@ -213,6 +219,28 @@ impl<'self, A, T: Iterator<A>> Iterator<A> for FilterIterator<'self, A, T> {
213219
}
214220
}
215221

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+
216244
pub struct EnumerateIterator<T> {
217245
priv iter: T,
218246
priv count: uint
@@ -432,6 +460,13 @@ mod tests {
432460
assert_eq!(i, expected.len());
433461
}
434462

463+
#[test]
464+
fn test_filter_map() {
465+
let it = Counter::new(0u, 1u).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+
435470
#[test]
436471
fn test_iterator_enumerate() {
437472
let xs = [0u, 1, 2, 3, 4, 5];

0 commit comments

Comments
 (0)