String::len() / is_empty() / contains()
| Since: | Rust 1.0(2015) |
|---|
Rust strings (String and &str) provide many methods for getting the length, checking for emptiness, searching, and testing prefixes or suffixes. Commonly used methods include len(), is_empty(), contains(), starts_with(), and ends_with().
Syntax
let s = String::from("Hello, Rust!");
// Returns the number of bytes (not the number of characters).
let len = s.len(); // 12 (ASCII characters are 1 byte each)
// Returns whether the string is empty.
let empty = s.is_empty(); // false
let has = s.contains("Rust"); // true
let starts = s.starts_with("Hello"); // true
let ends = s.ends_with("!"); // true
let idx = s.find("Rust"); // Some(7)
// Retrieves all match positions.
let positions: Vec<_> = s.match_indices("l").collect();
Method List
| Method | Description |
|---|---|
| s.len() | Returns the number of bytes in the string (not the number of characters). |
| s.is_empty() | Returns whether the string is empty (i.e., len() == 0). |
| s.contains(pattern) | Returns true if the string contains the given pattern. |
| s.starts_with(prefix) | Returns true if the string starts with the given string or character. |
| s.ends_with(suffix) | Returns true if the string ends with the given string or character. |
| s.find(pattern) | Returns the byte offset of the first match as Option<usize>. |
| s.rfind(pattern) | Returns the byte offset of the last match as Option<usize>. |
| s.match_indices(pattern) | Returns an iterator over all match positions and their substrings. |
| s.chars().count() | Returns the number of Unicode characters (handles multibyte characters such as Japanese). |
| s.is_ascii() | Returns whether all characters in the string are ASCII characters. |
Sample Code
sample_string_len_isempty_contains.rs
fn main() {
let s = String::from("Hello, Rust! Rust is wonderful.");
// Difference between byte length and character count.
println!("len (bytes): {}", s.len());
println!("chars().count() (characters): {}", s.chars().count());
// Checking for empty strings.
let empty = String::new();
let non_empty = String::from("hello");
println!("empty.is_empty(): {}", empty.is_empty());
println!("non_empty.is_empty(): {}", non_empty.is_empty());
println!();
// contains, starts_with, and ends_with.
println!("Contains 'Rust': {}", s.contains("Rust"));
println!("Contains 'Python': {}", s.contains("Python"));
println!("Starts with 'Hello': {}", s.starts_with("Hello"));
println!("Ends with '.': {}", s.ends_with("."));
println!("Ends with 'Rust': {}", s.ends_with("Rust"));
println!();
// find (first position).
match s.find("Rust") {
Some(i) => println!("First position of 'Rust': {}", i),
None => println!("'Rust' not found"),
}
match s.find("Python") {
Some(i) => println!("First position of 'Python': {}", i),
None => println!("'Python' not found"),
}
// rfind (last position).
if let Some(i) = s.rfind("Rust") {
println!("Last position of 'Rust': {}", i);
}
println!();
// match_indices (all matches).
let text = "maple manor";
let positions: Vec<_> = text.match_indices("ma").collect();
println!("Positions of 'ma' in 'maple manor': {:?}", positions);
// ASCII check.
println!("'Hello' is ASCII: {}", "Hello".is_ascii());
println!("'Hello world' is ASCII: {}", "Hello world".is_ascii());
// Practical example: validating user input.
let input = " ";
if input.trim().is_empty() {
println!("\nInput is empty");
}
}
Compile with the following command:
rustc string_len_isempty_contains.rs ./string_len_isempty_contains len (bytes): 31 chars().count() (characters): 31 empty.is_empty(): true non_empty.is_empty(): false Contains 'Rust': true Contains 'Python': false Starts with 'Hello': true Ends with '.': true Ends with 'Rust': false First position of 'Rust': 7 'Python' not found Last position of 'Rust': 13 Positions of 'ma' in 'maple manor': [(0, "ma"), (6, "ma")] 'Hello' is ASCII: true 'Hello world' is ASCII: true Input is empty
Common Mistakes
Mistake 1: Confusing len() with character count
len() returns the byte count. For strings containing multibyte characters such as Japanese text, you need chars().count() to get the number of characters.
string_len_mistake1.rs
fn main() {
let s = "user_a"; // all ASCII, 1 byte per char
println!("len()={}", s.len()); // 11 (bytes)
println!("chars().count()={}", s.chars().count()); // 11 (chars)
// For ASCII text both values are equal.
// For Japanese text (e.g., "東京都"), len()=9 but chars().count()=3.
// Use chars().count() when character-based comparison is needed.
if s.chars().count() == 11 {
println!("11 characters");
}
}
Compile with the following command:
rustc string_len_mistake1.rs ./string_len_mistake1 len()=11 chars().count()=11 11 characters
Mistake 2: Confusing find()'s return value with a character index
find() returns a byte offset, not a character index. For strings with multibyte characters, the byte offset and character index will differ. The returned offset can be used for slicing, but it does not mean "which character number".
string_find_note.rs
fn main() {
let s = "Hello, World!";
// find() returns the byte offset of the match (not the character index).
if let Some(idx) = s.find("World") {
println!("byte offset: {}", idx); // 7
println!("slice: {}", &s[idx..]); // "World!" — correct slice usage
}
// To get the character index (which character number), use position().
let char_pos = s.chars().position(|c| c == 'W');
println!("char index: {:?}", char_pos); // Some(7)
// For ASCII text the byte offset and char index happen to be equal.
// For multibyte text they will differ.
}
Compile with the following command:
rustc string_find_note.rs ./string_find_note byte offset: 7 slice: World! char index: Some(7)
Notes
Rust strings are UTF-8 encoded, and len() returns the number of bytes. When the string contains multibyte characters such as Japanese, the byte length and character count will differ. Use s.chars().count() to get the number of characters.
find() returns a byte offset. This offset is guaranteed to be on a character boundary, so you can use it for slicing like &s[0..idx]. However, slicing at an index that falls in the middle of a multibyte character will cause a panic.
len() returns the number of bytes, not the number of Unicode code points. When you need the character count, always use chars().count().
For string replacement, splitting, and trimming, see String::replace() / split() / trim().
If you find any errors or copyright issues, please contact us.