Referências e Borrowing
Uma referência permite usar um valor sem tomar seu ownership — escrita com &. O dono original mantém o valor, e a referência apenas toma emprestado (borrow) o acesso a ele temporariamente.
fn main() {
let s1 = String::from("hello");
let len = calculate_length(&s1);
println!("The length of '{}' is {}.", s1, len);
}
fn calculate_length(s: &String) -> usize {
s.len()
}The length of 'hello' is 5.
calculate_length toma emprestado s1 através de uma referência em vez de tomar seu ownership, então s1 continua perfeitamente usável de volta em main depois da chamada.
Referências mutáveis
Uma referência mutável, &mut T, permite que uma função modifique o valor que ela toma emprestado. O Rust permite isso, mas com uma restrição crucial: você pode ter ou uma referência mutável, ou qualquer número de referências imutáveis, a um valor por vez — nunca ambas.
fn main() {
let mut s = String::from("hello");
change(&mut s);
println!("{}", s);
}
fn change(s: &mut String) {
s.push_str(", world");
}hello, world
Como é um conflito de borrow real
Isto é genuinamente o que o rustc reporta quando você tenta criar uma referência mutável enquanto uma imutável ainda está em uso — capturado de uma execução real, não escrito para parecer plausível:
fn main() {
let mut s = String::from("hello");
let r1 = &s;
let r2 = &mut s;
println!("{}, {}", r1, r2);
}error[E0502]: cannot borrow `s` as mutable because it is also borrowed as immutable
--> main.rs:5:14
|
4 | let r1 = &s;
| -- immutable borrow occurs here
5 | let r2 = &mut s;
| ^^^^^^ mutable borrow occurs here
6 |
7 | println!("{}, {}", r1, r2);
| -- immutable borrow later used here
error: aborting due to previous error
For more information about this error, try `rustc --explain E0502`.Essa regra é o que descarta data races por completo, em tempo de compilação — duas partes de um programa nunca podem acabar lendo e escrevendo os mesmos dados ao mesmo tempo, porque o compilador simplesmente não deixa compilar o código que permitiria isso.
Próximo: strings e slices — a diferença entre um String com ownership e um &str emprestado (borrowed).
Practice Exercise
Escreva uma função word_count(s: &String) -> usize que retorne o número de palavras em s usando s.split_whitespace().count(). Chame-a com uma referência a um String contendo "the quick brown fox" e imprima o resultado.