Skip to main content
In this lesson, we explore the essential rules governing slices in Rust, focusing on memory safety and proper borrowing practices. Slices, much like references, must follow strict borrowing rules to prevent data races and dangling references. The key rules to keep in mind are:
  1. Slices must always point to valid data.
  2. You can have either one mutable slice or any number of immutable slices to a piece of data—but not both at the same time.
  3. Slices must not outlive the data they reference.
Rust’s borrow checker enforces these rules, ensuring that your code remains both safe and efficient.
Always ensure that any slice in your code points to valid and in-scope data. This is crucial to prevent runtime errors and data corruption.

Dangling Slice Prevention

Rust prevents the creation of dangling slices by enforcing that a slice cannot outlive its underlying data. Consider the following example, where using a slice after the array goes out of scope results in a compile-time error:
If you were to uncomment the println! statement, the Rust compiler would generate an error because the array arr is no longer valid when the slice is accessed.

Rule 2: Multiple Immutable Slices

At any given time, Rust enforces that you can either have one mutable slice or any number of immutable slices—but cannot mix the two. The following example demonstrates the use of multiple immutable slices:
In this example, both slice1 and slice2 reference parts of the string s and coexist safely since they are immutable. For mutable slices, observe this scenario:
In this case, the mutable slice allows the modification of the array’s elements, with the change reflected in the original data.

Mixing Mutable and Immutable Slices

Combining mutable and immutable slices for the same piece of data leads to a compile-time error. For example, creating a mutable slice while existing immutable references are still active will result in an error:
However, by limiting the scope of the immutable references, you can later create a mutable reference. The following example demonstrates this best practice:
This approach ensures that the mutable reference does not conflict with any active immutable references, maintaining Rust’s guarantees for data safety.
Mixing mutable and immutable references in overlapping scopes is disallowed in Rust. Always structure your code to manage reference scopes properly, ensuring that mutable references are only introduced once all immutable references have expired.

Watch Video

Practice Lab