Rust Ownership

If you’ve heard anything about Rust, you’ve probably heard about ownership.
It’s the most important concept in the language because it’s how Rust guarantees memory safety without a garbage collector.

Don’t worry if this sounds complicated—we’ll take it slowly and explain with examples.

What Is Ownership? #

In Rust, every piece of data has exactly one owner.

  • The owner is usually a variable that holds the data.
  • When the owner goes out of scope, the data is automatically cleaned up.

This means you don’t have to manually free memory, and you don’t risk memory leaks. For example:

fn main() {
    let name = String::from("Alice");
    println!("Hello, {}", name);
} // name goes out of scope here, and memory is freed automatically
Code language: Rust (rust)

In this example:

  • name is the owner of the string "Alice".
  • When main ends, name goes out of scope, and Rust automatically frees the memory.

No free(), no garbage collector—Rust handles it.

Moving Ownership #

What happens if we assign one variable to another?

fn main() {
    let name = String::from("Alice");
    let other = name;  // ownership moves to 'other'

    // println!("{}", name);  // ❌ ERROR: name is no longer valid
    println!("{}", other);   // ✅ works
}
Code language: Rust (rust)

Here’s what happened:

  • name owned "Alice".
  • When we assigned it to other, ownership moved to other.
  • name is no longer valid.

Rust does this to prevent double freeing the same memory.

Cloning Instead of Moving #

If you want two independent copies, you can use .clone():

fn main() {
    let name = String::from("Alice");
    let other = name.clone();  // deep copy

    println!("name: {}, other: {}", name, other);
}
Code language: Rust (rust)

Now both name and other own their own copies of the string.

Borrowing with References #

Sometimes you don’t want to give away ownership—you just want to borrow the value. Rust lets you do this with &.

fn main() {
    let name = String::from("Alice");
    greet(&name);  // borrow instead of move

    println!("Back in main: {}", name); // ✅ still valid
}

fn greet(person: &String) {
    println!("Hello, {}", person);
}
Code language: Rust (rust)

In this example:

  • &name means “borrow name for a moment.”
  • The function greet uses the borrowed value, but doesn’t take ownership.
  • name is still valid afterward.

Why Ownership Matters #

The ownership system helps Rust prevent:

  • Dangling pointers – using memory after it’s freed.
  • Double frees – freeing memory twice.
  • Data races – unsafe memory access across threads.

This is how Rust gives you safety and performance at the same time.

Summary #

  • Every value in Rust has exactly one owner.
  • When the owner goes out of scope, the value is freed.
  • Assigning variables moves ownership.
  • Use .clone() if you need a copy.
  • Use & to borrow data without taking ownership.
Was this Helpful ?