137. Vec::retain_mut — Filter and Edit In Place, In One Pass
retain decides who stays, but its closure only sees &T — so when you also want to tweak the survivors, you end up making two passes. retain_mut collapses that into one.
The Problem
Imagine a Vec<Job> where each surviving job needs its retry counter bumped on the way through. With plain retain, the closure gets a shared reference, so the mutation has to happen separately:
| |
Two passes, two intent-leaks, and the predicate is duplicated. Refactor one and forget to refactor the other — welcome to a subtle bug.
retain_mut: One Pass, Mutable Access
Vec::retain_mut gives the closure a &mut T. Edit the element and return whether to keep it — same call:
| |
One scan, no duplicated predicate, and the order of the kept elements is preserved.
The Sneaky Trick: Mutate-Then-Check
The mutation happens before the closure returns, so a retain_mut can also normalize values and then filter on the normalized form:
| |
Trim everything, then drop the blanks — without ever allocating a second Vec.
When to Reach for It
Use retain_mut whenever the keep/drop decision and an in-place edit travel together. Same goes for VecDeque::retain_mut and LinkedList::retain_mut — same shape, same payoff. If the closure is purely read-only, stick with retain and keep the intent narrow.