Processing with iterators
- Rust course
- Intermediate
- Lesson 63/115
- 6 min
Chain commands with iterators.
Processing with iterators
The search command must filter the notes together with their numbers. An enumerate and filter chain does this without building an intermediate collection:
impl Defter {
fn ara(&self, sorgu: &str) -> Vec<(usize, &String)> {
let s = sorgu.to_lowercase();
self.notlar
.iter()
.enumerate()
.filter(|(_, n)| n.to_lowercase().contains(&s))
.map(|(i, n)| (i + 1, n))
.collect()
}
}Adding the number before filter matters; otherwise the displayed number wouldn't reflect the note's real position.
Summary statistics
Iterators are ideal for short reports too:
let toplam_karakter: usize = d.notlar.iter().map(|n| n.chars().count()).sum();
let en_uzun = d.notlar.iter().max_by_key(|n| n.chars().count());
println!("{} not, {} karakter, en uzun: {:?}",
d.notlar.len(), toplam_karakter, en_uzun);Practice Search notes
Add the ara method to Defter. Add the notes "süt al", "kod yaz" and "süt faturası", and print the results of ara("süt") as N. note.
Starter code
struct Defter {
notlar: Vec<String>,
}
impl Defter {
fn new() -> Self {
Self { notlar: Vec::new() }
}
fn ekle(&mut self, metin: String) {
self.notlar.push(metin);
}
}
fn main() {
// buraya yaz
}Sample solution
struct Defter {
notlar: Vec<String>,
}
impl Defter {
fn new() -> Self {
Self { notlar: Vec::new() }
}
fn ekle(&mut self, metin: String) {
self.notlar.push(metin);
}
}
impl Defter {
fn ara(&self, sorgu: &str) -> Vec<(usize, &String)> {
let s = sorgu.to_lowercase();
self.notlar
.iter()
.enumerate()
.filter(|(_, n)| n.to_lowercase().contains(&s))
.map(|(i, n)| (i + 1, n))
.collect()
}
}
fn main() {
let mut d = Defter::new();
for n in ["süt al", "kod yaz", "süt faturası"] {
d.ekle(n.to_string());
}
for (i, n) in d.ara("süt") {
println!("{}. {}", i, n);
}
}Expected output
1. süt al 3. süt faturası
Questions and answers
Review the lesson questions together with their answers. To test yourself, solve the lesson interactively.
1 What would happen if <code>enumerate</code> were called after <code>filter</code>?
- Numbers would count 1, 2, 3 among the matches only Correct answer
- Compile error
- The result wouldn't change
- Panic
Explanation: The order of adapters changes the meaning; since the delete command needs the real number, enumerate must come first.
2 Filter the matches
.enumerate()
.____(|(_, n)| n.to_lowercase().contains(&s))
.enumerate()
.filter(|(_, n)| n.to_lowercase().contains(&s))
Explanation: filter keeps the (number, note) pairs that meet the condition.
3 Query and matching numbers
| Term | Meaning |
|---|---|
"süt" |
1, 3 |
"KOD" |
2 |
"fatura" |
3 |
"çay" |
None |