Rust Tutorial · Ownership and Borrowing · Lesson 11 of 29

Rust Slices and Strings

String versus &str, string slices, array slices, and working with UTF-8 text correctly.

Create a free account to save this page, take notes and track your progress. Sign in

String and &str

  • String is an owned, growable UTF-8 string on the heap.
  • &str is a borrowed string slice: a view into a string (string literals are &'static str).

Functions that only read text should take &str; they then accept both.

String, &str and slices
fn shout(text: &str) -> String {
    text.to_uppercase() + "!"
}

fn main() {
    let owned: String = String::from("hello rust");
    let literal: &str = "hi";
    println!("{} / {}", shout(&owned), shout(literal));
    let first_word = owned.split_whitespace().next().unwrap_or("");
    println!("first word: {first_word}");
    let numbers = [10, 20, 30, 40];
    let middle: &[i32] = &numbers[1..3];
    println!("{middle:?}");
}

Output

HELLO RUST! / HI!
first word: hello
[20, 30]

Run this on your computer — see “Get Started” for setup.

Slices and UTF-8

&s[0..4] slices by bytes. Characters can take several bytes, so iterate with .chars() when you need characters:

Strings are UTF-8
fn main() {
    let word = "café";
    println!("bytes: {}, chars: {}", word.len(), word.chars().count());
    println!("first 3 bytes: {}", &word[0..3]);
    let reversed: String = word.chars().rev().collect();
    println!("reversed: {reversed}");
}

Output

bytes: 5, chars: 4
first 3 bytes: caf
reversed: éfac

Run this on your computer — see “Get Started” for setup.

Test yourself

What should a function that only reads text take as a parameter?

  1. String
  2. &str
  3. &String
  4. char
Show answer

Answer: &str

&str accepts string literals, slices and &String (through deref coercion).

Was this page helpful?