You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Note:
This is not a bug or issue, although it can still be considered a good idea to further explain certain things (in the hint text?).
Hi.
Generally the way I play around the Rustlings exercises is by experimenting with those a lot further than just the single thing officially asked for to solve. Simply because I like to learn and understand as much as possible.
And in this way I now noticed something that I believe is really worth asking an explanation about.
So in as_ref_mut.rs I filled in the AsMut trait bound with u32 as a type parameter for this function and I added the multiply implementation:
// Squares a number using as_mut().
// TODO: Add the appropriate trait bound.
fn num_sq<T: AsMut<u32>>(arg: &mut T) {
// TODO: Implement the function body.
*arg.as_mut() *= *arg.as_mut();
}
But in my opion, this could be done far better, by making the function even more generic, and replaced the hard u32 bound by the more generic MulAssign + Copy, so that this function is allowed to work with many numeric types:
// Squares a number using as_mut().
// TODO: Add the appropriate trait bound.
fn num_sq<T: AsMut<impl MulAssign + Copy>>(arg: &mut T) {
// TODO: Implement the function body.
*arg.as_mut() *= *arg.as_mut();
}
However, interestingly enough, this does not compile ...
error[E0499]: cannot borrow `*arg` as mutable more than once at a time
--> exercises/conversions/as_ref_mut.rs:30:23
|
30 | *arg.as_mut() *= *arg.as_mut();
| ------------------^^^---------
| || |
| || second mutable borrow occurs here
| |first mutable borrow occurs here
| first borrow later used here
|
help: try adding a local storing this...
--> exercises/conversions/as_ref_mut.rs:30:23
|
30 | *arg.as_mut() *= *arg.as_mut();
| ^^^^^^^^^^^^
help: ...and then using that local here
--> exercises/conversions/as_ref_mut.rs:30:5
|
30 | *arg.as_mut() *= *arg.as_mut();
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
I decided to follow the compiler's advice and created an extra variable first, explicitly borrowing the thing just 1 time.
Turns out, it works, this code succeeds:
// Squares a number using as_mut().
// TODO: Add the appropriate trait bound.
fn num_sq<T: AsMut<impl MulAssign + Copy>>(arg: &mut T) {
// TODO: Implement the function body.
let arg = arg.as_mut();
*arg *= *arg;
}
Alright.
But how is this possible? Why does the compiler accept a duplicate as_mut() borrow in the first case where I am directly working with u32 types only, but not when I am working via a MulAssign + Copy trait bound?
What am I missing? Is there another trait bound that I don't know about? Or is this some intrinsic compiler behaviour for numeric types?
The text was updated successfully, but these errors were encountered:
Note:
This is not a bug or issue, although it can still be considered a good idea to further explain certain things (in the hint text?).
Hi.
Generally the way I play around the Rustlings exercises is by experimenting with those a lot further than just the single thing officially asked for to solve. Simply because I like to learn and understand as much as possible.
And in this way I now noticed something that I believe is really worth asking an explanation about.
So in
as_ref_mut.rs
I filled in the AsMut trait bound with u32 as a type parameter for this function and I added the multiply implementation:But in my opion, this could be done far better, by making the function even more generic, and replaced the hard u32 bound by the more generic MulAssign + Copy, so that this function is allowed to work with many numeric types:
However, interestingly enough, this does not compile ...
I decided to follow the compiler's advice and created an extra variable first, explicitly borrowing the thing just 1 time.
Turns out, it works, this code succeeds:
Alright.
But how is this possible? Why does the compiler accept a duplicate as_mut() borrow in the first case where I am directly working with u32 types only, but not when I am working via a MulAssign + Copy trait bound?
What am I missing? Is there another trait bound that I don't know about? Or is this some intrinsic compiler behaviour for numeric types?
The text was updated successfully, but these errors were encountered: