Let's try to compile this code:
trait Bar {
fn bar(&mut self);
}
fn foo(a1: &mut Bar, j: usize) {
let a = [a1];
a[0].bar(); //compilation ok
a[j % 2].bar();
}
fn main() {}
Compilation error:
error[E0596]: cannot borrow immutable local variable `a` as mutable
--> src/main.rs:8:5
|
6 | let a = [a1];
| - consider changing this to `mut a`
7 | a[0].bar(); //compilation ok
8 | a[j % 2].bar();
| ^ cannot borrow mutably
Why is a[0].bar()
OK, but a[j % 2].bar()
fails? Is it a compiler bug?
Is it a compiler bug?
Yes. It is fixed in Rust 1.25.0-nightly (2018-01-09 61452e506f0c88861cccaeea4ced3419bdb3cbe0) by PR 47167
The short version is that there are two ways of performing indexing, referred to as "builtin indexing" and "overloaded indexing". As you might be able to guess from the names, one is more intrinsic to the compiler and the other is more user-customizable.
In this case, the overloaded indexing is performing an unneeded borrow of the array, triggering the warning. You can work around the problem by simplifying the compilers job of type inference:
fn foo(a1: &mut Bar, j: usize) {
let a = [a1];
let x: usize = j % 2;
a[x].bar();
}
By explicitly stating the index is a usize
, the code will now use the builtin indexing.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With