45. get_disjoint_mut — Multiple Mutable References at Once
The borrow checker won’t let you hold two &mut refs into the same collection — even when you know they don’t overlap. get_disjoint_mut fixes that without unsafe.
The problem
You want to update two elements of the same Vec together, but the compiler won’t allow two mutable borrows at once:
| |
The borrow checker doesn’t know indices 0 and 2 are different slots — it just sees two &mut to the same Vec. The classic escape hatches (split_at_mut, unsafe, RefCell) all feel like workarounds for something that should just work.
get_disjoint_mut to the rescue
Stabilized in Rust 1.86, get_disjoint_mut accepts an array of indices and returns multiple mutable references — verified at runtime to be non-overlapping:
| |
The Result is Err only if an index is out of bounds or indices overlap. Duplicate indices are caught at runtime and return Err — no silent aliasing bugs.
Works on HashMap as well
HashMap gets the same treatment. The return type is [Option<&mut V>; N] — one Option per key, since keys can be missing:
| |
Passing duplicate keys to the HashMap version panics — the right tradeoff for a bug that would otherwise silently produce undefined behavior.
When to reach for it
- Swapping or combining two elements in a
Vecwithoutsplit_at_mutgymnastics - Updating multiple
HashMapentries in one pass - Any place you’d have used
unsafeorRefCelljust to hold two&mutinto the same container
If your indices or keys are known not to overlap, get_disjoint_mut is the clean, safe answer.