⚡ Lehrpfad 3: Traits, Generics & Smart Pointer

Rust 11: Closures & Iterator Pipelines

Meistere funktionale Programmierung in Rust: Closures (Fn, FnMut, FnOnce), Custom-Iteratoren und hocheffiziente Zero-Cost Iterator-Pipelines.

📂 Dateien dieser Lerneinheit:
📄 aufgabe.rs (Startercode) 🧪 test_aufgabe.rs (Tests) 💡 musterloesung.rs (Lösung) 📖 README.md

⚡ 1. Closures & die Trait-Hierarchie (Fn, FnMut, FnOnce)

Ein Closure ist eine anonyme Funktion, die Variablen aus ihrer Umgebung einfangen (capturen) kann. Der Rust-Compiler leitet automatisch das restriktivste Trait ab:

                        ┌──────────────┐
                        │    FnOnce    │ (Konsumiert Umgebung / Move, 1x aufrufbar)
                        └──────┬───────┘
                               ▲
                        ┌──────┴───────┐
                        │    FnMut     │ (Verändert Umgebung &mut, mehrfach aufrufbar)
                        └──────┬───────┘
                               ▲
                        ┌──────┴───────┐
                        │      Fn      │ (Liest Umgebung unveränderlich &T, nebenläufig nutzbar)
                        └──────────────┘
// 1. Fn: Liest Referenz
let factor = 2;
let double = |x: i32| x * factor;

// 2. FnMut: Mutiert Zustand
let mut count = 0;
let mut inc = || { count += 1; count };

// 3. FnOnce / move: Übernimmt Ownership
let text = String::from("Rust");
let consume = move || println!("Taken: {}", text);

🛡️ 2. Der Iterator Trait & Adapter Pipelines

In Rust sind Iteratoren lazy (träge) – Berechnungen finden erst statt, wenn ein Consumer wie .collect(), .sum() oder .fold() die Pipeline konsumiert.

pub trait Iterator {
    type Item;
    fn next(&mut self) -> Option<Self::Item>;
}

// Zero-Cost Pipeline:
let sum_of_even_squares: u64 = (1..=100)
    .filter(|&x| x % 2 == 0)
    .map(|x| x * x)
    .sum();
🏭 Didaktische Analogie: Das Montageband in der Fabrik

Ein Iterator ist wie ein Fließband: .filter() und .map() sind Bearbeitungsstationen am Band. Das Band bewegt sich jedoch kein Stück, bis am Ende der Fertigwaren-Empfänger (.collect()) das Paket anfordert!

📑 3. Cheat-Sheet: Wichtige Iterator-Adapter

Adapter / Consumer Signatur-Beispiel Beschreibung
.map(f) iter.map(|x| x * 2) Transformiert jedes Element 1:1
.filter(p) iter.filter(|x| *x > 10) Behält nur Elemente, die dem Prädikat entsprechen
.fold(init, f) iter.fold(0, |acc, x| acc + x) Aggregiert alle Werte in einen Akkumulator
.collect() iter.collect::<Vec<_>>() Wandelt Iterator in eine konkrete Kollektion um

🧠 Diagnostischer Selbst-Check

Überprüfe dein Verständnis von Ownership, Borrowing und Typensicherheit, bevor du die Übung in der Web-IDE bearbeitest.

🎯 Aufgaben & Checkliste in aufgabe.rs

💻 In Web-IDE öffnen → ← Zurück zu Rust 10 Weiter zu Rust 12: Smart Pointer →