DerefMut is a Rust standard trait for mutable dereferencing. It lets code modify the value reached through *value, and it requires Deref first. section 15.3.3
Its implementation follows the immutable Deref implementation:
- Import DerefMut alongside Deref. section 15.3.3
- Keep the associated Target type from Deref; DerefMut inherits it. section 15.3.3
- Implement deref_mut(&mut self) to return &mut Self::Target. section 15.3.3
Making a wrapped number mutable
A HoldsANumber value can implement Deref for read access and DerefMut for write access. With both traits, `*my_number = 30` changes the wrapped `u8`. Without DerefMut, the compiler reports that DerefMut is required to modify through the dereference. section 15.3.2 section 15.3.3
use std::ops::{Deref, DerefMut};
struct HoldsANumber(u8);
impl HoldsANumber {
fn prints_the_number_times_two(&self) {
println!("{}", self.0 * 2);
}
}
impl Deref for HoldsANumber {
type Target = u8;
fn deref(&self) -> &Self::Target {
&self.0
}
}
impl DerefMut for HoldsANumber {
fn deref_mut(&mut self) -> &mut Self::Target {
&mut self.0
}
}
fn main() {
let mut my_number = HoldsANumber(20);
*my_number = 30; #1
println!("{:?}", my_number.checked_sub(100));
my_number.prints_the_number_times_two();
}
Inspect the complete implementation and the assignment through the mutable dereference. section 15.3.3
DerefMut is powerful but should fit the meaning of the type. It works naturally for simple wrapper types such as smart pointers; using it to expose an unrelated field can make operations like -= or push difficult to understand. Named methods may communicate complex behavior more clearly. section 15.3.4 section 15.4
