Beginner Fundamentals
Ownership
Ownership is Rust’s core feature for managing memory safely without a garbage collector. The compiler enforces a set of rules at compile time.
The rules
- Each value has a single owner.
- There can be only one owner at a time.
- When the owner goes out of scope, the value is dropped (freed).
Scope and drop
fn main() {
{
let s = String::from("hello"); // s owns the string
println!("{}", s);
} // s goes out of scope here, memory is freed automatically
}
Move
When you assign one variable to another for a heap value, ownership moves. The original variable can no longer be used.
fn main() {
let a = String::from("data");
let b = a; // ownership moves from a to b
// println!("{}", a); // error: a was moved
println!("{}", b); // ok
}
Moves into functions
Passing a value to a function also moves it, unless the type is Copy (like integers).
fn consume(s: String) {
println!("{}", s);
} // s is dropped here
fn main() {
let text = String::from("hi");
consume(text);
// text is no longer usable here
}
Ownership prevents double frees and dangling pointers. To use a value without taking ownership, you borrow it, which is the next lesson.