assert_eq!
The assert_eq! macro asserts that two expressions are equal (left == right via PartialEq), and if they are not equal, panics and prints the Debug ({:?}) values of both operands side by side.
Why assert_eq!(a, b) Beats assert!(a == b)
When assert!(a == b) fails, the panic message only prints the literal expression text assertion failed: a == b without showing what a and b actually evaluated to! By contrast, assert_eq!(a, b) binds &left and &right once, compares *left_val == *right_val, and formats both values with {:?} on failure:
| Macro | Trait Bounds on Operands | Failure Output |
|---|---|---|
assert!(a == b) |
PartialEq |
assertion failed: a == b (values hidden) |
assert_eq!(a, b) |
PartialEq + Debug |
Prints assertion 'left == right' failed along with left: ... and right: ... |
Single-Evaluation Guarantee and Custom Messages
Like a well-designed hygienic macro, assert_eq!(left, right) expands to match (&left, &right) { (left_val, right_val) => ... }, guaranteeing that left and right are each evaluated exactly once even when an assertion fails. You can also pass an optional format string and arguments as the third parameter:
#[derive(Debug, PartialEq, Eq)]
struct Point {
x: i32,
y: i32,
}
fn translate(p: Point, dx: i32, dy: i32) -> Point {
Point {
x: p.x + dx,
y: p.y + dy,
}
}
fn main() {
let start = Point { x: 2, y: 3 };
let moved = translate(start, 10, -1);
assert_eq!(
moved,
Point { x: 12, y: 2 },
"translation by (10, -1) produced wrong coordinates"
);
println!("Verified point: {moved:?}");
}
Verified point: Point { x: 12, y: 2 }
Diagnostic Output When assert_eq! Fails
fn main() {
let actual = vec![10, 20, 99];
let expected = vec![10, 20, 30];
assert_eq!(actual, expected, "vector mismatch at final element");
}
thread 'main' panicked at src/main.rs:4:5:
assertion `left == right` failed: vector mismatch at final element
left: [10, 20, 99]
right: [10, 20, 30]