Two coercions run so often that they become invisible — and then confusing the first time they do not fire.
Deref coercion. &String becomes &str, &Vec<T> becomes &[T], &Box<T> becomes &T. The compiler inserts the conversion at a call site whenever the target type does not match but a Deref impl bridges them.
fn describe(s: &str) -> usize { s.len() }
let owned = String::from("soroban");
describe(&owned); // &String coerced to &str — no allocation, no copy
This is why you take &str in a parameter and String in a struct field: the parameter accepts both, the field owns its data.
