iterators_rfoxmich/
lib.rs

1//!  This file contains a pair of types
2//!  which show how to use closures (Shoes and shoes_in_my_size)
3//! and how to create a custom iterator (Counter).
4
5///
6/// Shoe 
7/// 
8///    Struct that captures  a shoe size and style. 
9///
10#[derive(PartialEq, Debug)]
11pub struct Shoe {
12    size: u32,
13    style: String,              // Unimportant for this.
14}
15///
16/// shoes_in_my_size
17/// 
18///    Given a vector of shoes, and a shoe size, returns a vector
19///    of shoes that only contains the shoes that match the size. 
20/// 
21pub fn shoes_in_my_size(shoes : Vec<Shoe>, shoe_size : u32) -> Vec<Shoe> {
22    shoes.into_iter()     //    +-> Env capture of shoe_size.
23        .filter(|s| s.size == shoe_size)
24        .collect()
25}
26// Sample a custom iterator that counts 1 -5:.alloc
27
28///
29/// 
30///    Provides a counter that behaves like an
31///    iterator only counting to 5 before it is 
32///    fully consumed.
33pub struct Counter {
34    count : u32
35}
36impl Counter {
37    ///
38    /// Constructs a new Counter object. 
39    /// 
40    /// # Examples
41    /// 
42    /// ```
43    ///  use iterators::Counter;
44    ///  let c = Counter::new();
45    /// 
46    /// ```
47    /// 
48    pub fn new() -> Counter { 
49        Counter {count:0} 
50    }
51}
52impl Iterator for Counter {
53    type Item= u32;
54    ///
55    /// Returns the next value from a Counter
56    /// 
57    /// # Examples
58    ///
59    ///  ```
60    /// 
61    /// use iterators::Counter;
62    /// let mut a = Counter::new();
63    /// 
64    /// let value = match a.next() {
65    ///    Some(i) => i,
66    ///    None => 5
67    /// };
68    /// assert_eq!(value, 1);
69    /// 
70    /// ```
71    /// Note that this code 'pegs' the iterator at 5
72    /// once it's consumed
73    /// 
74    fn next(&mut self) -> Option<Self::Item> {
75        self.count += 1;
76        if self.count < 6 {
77            Some(self.count)
78        } else {
79            None
80        }
81    }
82}
83
84#[cfg(test)]
85mod tests {
86    use super::Shoe;
87    use super::Counter;
88    use super::shoes_in_my_size;
89    #[test]
90    fn iter_test() {
91        let v = vec![1,2,3];
92
93        let mut v1_iter = v.iter();
94        assert_eq!(v1_iter.next(), Some(&1));
95        assert_eq!(v1_iter.next(), Some(&2));
96        assert_eq!(v1_iter.next(), Some(&3));
97        assert_eq!(v1_iter.next(), None);
98    }
99    // Shoe size demo... using iterators that capture env.alloc
100
101
102    #[test]
103    fn sum_test() {
104        let v = vec![3,4,5,6];
105        let v_iter = v.iter();
106        let c_iter = v_iter.cloned();
107        let total :u32 = c_iter.sum();              // Consumes the iterator...
108        assert_eq!(total, 3+4+5+6);
109        // assert_eq!(v_iter.next(), Some(&3));       // So this is not legal.
110    }
111    #[test]
112    fn map_test() {
113        let v = vec![3,4,5];
114        
115        let v1 : Vec<_> =  v.iter().map(|x|  *x+1).collect();
116        let mut v_i = v1.iter();
117        assert_eq!(v_i.next(), Some(&4));
118        assert_eq!(v_i.next(), Some(&5));
119        assert_eq!(v_i.next(), Some(&6));
120        assert_eq!(v_i.next(), None);
121    }
122    #[test]
123    fn filter_by_size() {
124        let shoes = vec![
125            Shoe {size: 10, style: String::from("sneakers")},
126            Shoe {size: 11, style: String::from("Oxford")},
127            Shoe {size: 10, style: String::from("boot")},
128        ];
129
130        let in_my_size = shoes_in_my_size(shoes, 10);
131        assert_eq!(in_my_size, vec![
132            Shoe {size: 10, style: String::from("sneakers")},
133            Shoe {size: 10, style: String::from("boot")},
134        ]
135        );
136    }
137    #[test]
138    fn counter_test_1() {
139        let mut c_i = Counter::new();
140        
141
142        assert_eq!(c_i.next(), Some(1));
143        assert_eq!(c_i.next(), Some(2));
144        assert_eq!(c_i.next(), Some(3));
145        assert_eq!(c_i.next(), Some(4));
146        assert_eq!(c_i.next(), Some(5));
147        assert_eq!(c_i.next(), None);
148   }
149   #[test]
150   fn counter_test_2() {
151       let  c = Counter::new();
152       let result : Vec<u32> = c.filter(|x| x % 2 == 0).collect();
153       assert_eq!(
154           result, vec![2, 4]
155       );
156   }
157
158}