Option::take în Rust

Option: valori care pot lipsi Rust 1.0 (replace: 1.31)

take scoate valoarea și lasă None în loc; replace pune o valoare nouă și o returnează pe cea veche.

Sintaxă
fn take(&mut self) -> Option<T>
fn replace(&mut self, value: T) -> Option<T>

Ce face Option::take

take() mută valoarea afară din opțiune și lasă în locul ei None. Este felul obișnuit de a „lua” o valoare dintr-un câmp al unei structuri prin &mut, fără să copiezi și fără să lași câmpul neinițializat.

replace(valoare) pune Some(valoare) în opțiune și returnează ce era înainte (Some(vechi) sau None). Ambele lucrează pe loc, deci variabila trebuie să fie mut.

Parametri

Parametru Descriere
value La replace: noua valoare, pusă în Some.

Ce returnează

Valoarea de dinainte, ca Option<T>.

Exemple

Exemplul 1: Preluarea unei comenzi o singură dată

Prima preluare ia comanda și lasă None; a doua nu mai găsește nimic.

struct Casa {
    comanda_curenta: Option<String>,
}

impl Casa {
    fn preia(&mut self) -> Option<String> {
        self.comanda_curenta.take()
    }
}

fn main() {
    let mut casa = Casa { comanda_curenta: Some(String::from("2 cafele")) };
    println!("prima preluare: {:?}", casa.preia());
    println!("a doua preluare: {:?}", casa.preia());
    println!("rămas: {:?}", casa.comanda_curenta);
}

Rezultat

prima preluare: Some("2 cafele")
a doua preluare: None
rămas: None

Exemplul 2: replace returnează valoarea veche

Schimbăm orașul de livrare și aflăm ce era înainte.

fn main() {
    let mut oras: Option<&str> = None;

    let vechi = oras.replace("Iași");
    println!("vechi = {vechi:?}, acum = {oras:?}");

    let vechi = oras.replace("Cluj");
    println!("vechi = {vechi:?}, acum = {oras:?}");
}

Rezultat

vechi = None, acum = Some("Iași")
vechi = Some("Iași"), acum = Some("Cluj")

Greșeli frecvente

  • Încerci să muți valoarea dintr-un câmp prin &mut self cu let v = self.camp;: eroare cannot move out of. Folosește self.camp.take().
  • Uiți mut la variabilă: take și replace modifică opțiunea.

Comenzi înrudite

  • mem::take: Mută valoarea afară dintr-un loc mutabil și lasă în loc valoarea implicită a tipului (text gol, vector gol, 0).
  • mem::replace: Pune o valoare nouă într-un loc mutabil și returnează valoarea veche, mutată afară.
  • Option::as_ref: Transformă &Option<T> în Option<&T> (sau Option<&mut T>), ca să folosești valoarea fără să o muți din opțiune.
  • Option::get_or_insert_with: Dacă opțiunea este None, pune în ea valoarea calculată de funcție; apoi returnează o referință mutabilă la valoare.