Expert · Rust careers and interviews · topic 48 of 50 · 35 min
Interview questions: ownership, borrowing and lifetimes
Explanation
How to answer
Interviewers want to see that you understand why, not just that you memorised rules. A good structure: one-sentence definition, the reason it exists, a two-line example, and a common mistake. Practise saying answers out loud; explaining clearly is a skill.
Q1. What is ownership?
Model answer: "Ownership is how Rust manages memory without a garbage collector. Each value has one owner; there is one owner at a time; when the owner goes out of scope the value is dropped. The compiler checks this, so double frees and leaks from forgotten frees are prevented at compile time."
Q2. Move, Copy and Clone: what is the difference?
Model answer: "Assigning a heap-owning value like String moves it: only the pointer, length and capacity are copied and the old variable becomes invalid, to avoid a double free. Small stack-only types that implement Copy, such as integers and bool, are copied and both stay valid. clone() is an explicit deep copy that duplicates the heap data and costs time and memory."
Q3. What are the borrowing rules, and why?
Model answer: "At any time you can have either any number of shared references or exactly one mutable reference, and references must always be valid. This prevents data races and bugs like modifying a collection while iterating it. The checks happen at compile time, so there is no run-time cost."
Q4. String versus &str?
Model answer: "String owns growable UTF-8 text on the heap. &str is a borrowed view of some UTF-8 text: it can point into a String, a literal or another slice. I take &str as a function parameter because it accepts both, and return String when the function creates new text."
Q5. What is a lifetime? When do you write one?
Model answer: "A lifetime is the region of code where a reference is valid. The compiler infers most of them through elision rules. I write them when the compiler cannot tell how an output reference relates to the inputs, for example a function taking two &str and returning one of them, or a struct that holds a reference. Annotations describe relationships; they never extend how long anything lives."
fn longest<'a>(a: &'a str, b: &'a str) -> &'a str {
if a.len() >= b.len() { a } else { b }
}Q6. Why can a function not return a reference to a local variable?
Model answer: "The local is dropped when the function returns, so the reference would dangle. The compiler rejects it (E0106 or E0515). The fix is to return an owned value, like String, so ownership moves to the caller."
Q7. What are non-lexical lifetimes?
Model answer: "Since Rust 2018, a borrow lasts until its last use, not until the end of its block. So you can take a shared reference, use it, and then take a mutable one in the same block."
Q8. What does 'static mean?
Model answer: "As a lifetime on a reference, &'static T means the data lives for the entire program, like string literals. As a bound, T: 'static means the type holds no non-static references, which is why thread::spawn requires it: the thread might outlive any borrowed data."
Common interview mistakes
- Saying "Rust has no memory management". It has automatic, deterministic memory management through ownership.
- Saying a lifetime annotation "makes a value live longer". It does not.
- Saying clone is always bad. It is fine when data is small or a copy is truly needed; just know its cost.
- Long, rambling answers. Define, explain why, show a tiny example, stop.
Need help?
Stuck on a word or an idea? Search this course, or every course, and jump straight to the explanation or a worked question.
Try:
Watch the lesson
Interview questions: ownership, borrowing and lifetimes · 1/7
Almost every Rust interview starts with ownership. Answer with a definition, the reason, a tiny example, and a common mistake.
Prefer a video by a teacher? Find free videos on “rust interview questions ownership borrowing lifetimes” on YouTube ↗
In real life: A typical live-coding question
An interviewer at a fintech company shares this snippet and asks: "Why does this fail, and how would you fix it?" A strong candidate explains that the shared borrow first is still used after push needs a mutable borrow (E0502), that push may reallocate and leave first dangling, and offers two fixes: copy the value out, or use it before the push.
fn main() {
let mut balances = vec![500, 1200];
let first = &balances[0];
balances.push(300); // error[E0502]
println!("{first}");
}
// Fix 1: let first = balances[0]; (copy the i32)
// Fix 2: print first before calling pushPractice (0/3 done)
An interviewer asks: "Does a lifetime annotation make a value live longer?" Which answer is correct?
Which is the best one-line explanation of why Rust moves a String on assignment?
Record yourself (phone voice memo) answering Q1 to Q8 from this topic, each in under 60 seconds. Listen back and mark where you hesitated. Then rewrite your weakest two answers and record them again.
Quick quiz
Read more (free)
Related help
Before this, learn
This topic builds on these. If something here feels new, open them first.
Related topics
- Interview questions: traits, errors, pointers and concurrencyRust careers and interviews · same module
- Portfolio, open source and a learning planRust careers and interviews · same module
- Interview questions: KotlinKotlin and Android App Development · Android career path
- Interview questions: DartFlutter and Dart · Flutter careers and interviews
- The borrow checker in practiceBorrowing, slices and lifetimes
- Ownership and functionsOwnership: Rust's big idea
Questions people ask about this
Open a question to see the answer and why. The first ones are this topic's own quiz, so try the quiz above before you peek.
Which statement about non-lexical lifetimes is correct?
Answer: Borrows last until their last use
NLL ends borrows at their last use.
Why does thread::spawn require 'static data?
Answer: The thread may outlive any borrowed local data
Spawned threads can run after the caller returns.
What is the best fix for "returns a reference to data owned by the current function"?
Answer: Return an owned value
Move ownership out instead of borrowing a local.
Which parameter type is most flexible for read-only text?
Answer: &str
&str accepts literals, Strings and slices.
The compiler suggests adding 'static to a returned reference to a local String. What is usually the right fix?Related
Answer: Return the owned String instead
A local String is dropped at the end of the function; returning ownership is the clean fix.
From Lifetimes
What happens if you call a blocking function inside a tokio task?Related
Answer: It can stall other tasks on that worker thread
Blocking work belongs in spawn_blocking.
From Interview questions: traits, errors, pointers and concurrency
Which type should a ViewModel expose for screen state?Related
Which constructor type can return a cached instance?Related
Pass the quiz (60% or more) or mark this topic as done when you are ready.
Your progress is saved on this device only.
Next steps
- 2 more topics in “Rust careers and interviews” before its exam: Interview questions: traits, errors, pointers and concurrency, Portfolio, open source and a learning plan.
- Module 12 exam: Rust careers and interviews · 10 questions · 20 min, without help. 4 topics of this module still to finish first.
- 50 topics left in the course before the final exam.