Panic Basics
In this page:
panic!("message");
let value = result.unwrap(); // panics on Err or None
Triggering a Panic Explicitly
The panic! macro immediately stops normal program execution with the given message, used for situations that should truly never happen.
Example: Triggering a Panic Explicitly
// Entry point: execution of the program starts here
fn main() {
// Declare an immutable variable `should_continue`, set to `true`
let should_continue = true;
// Check whether `!should_continue`
if !should_continue {
panic!("This should never happen");
}
// Print "Program continued normally" to the console (with a trailing newline)
println!("Program continued normally");
}
Login to try C/C++/Java/PHP code in the editor
Panics from Built-in Operations
Several standard operations panic automatically on invalid input, such as indexing an array out of bounds. This example shows a safe check before it would happen.
Example: Panics from Built-in Operations
// Entry point: execution of the program starts here
fn main() {
// Declare an immutable variable `numbers`, set to `[1, 2, 3]`
let numbers = [1, 2, 3];
// Declare an immutable variable `index`, set to `2`
let index = 2;
// Check whether `index < numbers.len()`
if index < numbers.len() {
// Print "Safe access: {}" to the console, substituting in `numbers[index]` (with a trailing newline)
println!("Safe access: {}", numbers[index]);
// Otherwise, run this branch
} else {
// Print "Index out of bounds, avoided panic" to the console (with a trailing newline)
println!("Index out of bounds, avoided panic");
}
}
Login to try C/C++/Java/PHP code in the editor
Panic vs Result
panic! is appropriate for programming bugs and truly unrecoverable states, while Result is appropriate for expected, recoverable failure conditions that callers should be able to handle.
Example: Panic vs Result
// Define the function `safe_divide` taking `a`, `b` and returning a `Result<i32, &'static str>`
fn safe_divide(a: i32, b: i32) -> Result<i32, &'static str> {
// Check whether `b == 0`
if b == 0 {
Err("division by zero is an expected, recoverable error")
// Otherwise, run this branch
} else {
Ok(a / b)
}
}
// Entry point: execution of the program starts here
fn main() {
// Match on `safe_divide(10, 0)` and branch by pattern
match safe_divide(10, 0) {
Ok(v) => println!("{}", v),
Err(e) => println!("Handled gracefully: {}", e),
}
}
Login to try C/C++/Java/PHP code in the editor
Catching Panics with catch_unwind
In rare cases, std::panic::catch_unwind can catch a panic and prevent it from crashing the whole program, though this is uncommon and not a substitute for proper Result-based error handling.
Example: Catching Panics with catch_unwind
// Bring `std::panic` into scope
use std::panic;
// Entry point: execution of the program starts here
fn main() {
let result = panic::catch_unwind(|| {
// Print "About to panic inside catch_unwind" to the console (with a trailing newline)
println!("About to panic inside catch_unwind");
panic!("controlled panic");
});
// Match on `result` and branch by pattern
match result {
Ok(_) => println!("No panic occurred"),
Err(_) => println!("Panic was caught and handled"),
}
}
Login to try C/C++/Java/PHP code in the editor
- Using
panic!for ordinary, expected error conditions instead of returning aResultthat callers can handle gracefully. - Assuming a panic can always be caught and recovered from like an exception -- by default it unwinds and terminates the current thread's work.
- Not realizing indexing out of bounds, integer overflow (in debug builds), and
.unwrap()onNone/Errall trigger a panic automatically.
panic!("message")immediately stops normal execution and begins unwinding (or aborting) the program.- Common built-in operations like out-of-bounds indexing or
.unwrap()onNonetrigger a panic automatically. - Panics are meant for unrecoverable bugs, not for expected, everyday error conditions -- use
Resultfor those. RUST_BACKTRACE=1can be set when running a program to print a full backtrace when a panic occurs.
Chapter Quiz — Complete all 6 topics to unlock
0/6 topics done
Complete these topics first: