The mutual exclusion property of mutable references can be very limiting when
working with a composite structure. The borrow checker understands some basic
-stuff, but will fall over pretty easily. It *does* understand structs
+stuff, but will fall over pretty easily. It does understand structs
sufficiently to know that it's possible to borrow disjoint fields of a struct
simultaneously. So this works today:
work:
```rust,ignore
- let x = [1, 2, 3];
+ let mut x = [1, 2, 3];
let a = &mut x[0];
let b = &mut x[1];
println!("{} {}", a, b);
```
```text
- <anon>:3:18: 3:22 error: cannot borrow immutable indexed content `x[..]` as mutable
- <anon>:3 let a = &mut x[0];
- ^~~~
- <anon>:4:18: 4:22 error: cannot borrow immutable indexed content `x[..]` as mutable
- <anon>:4 let b = &mut x[1];
- ^~~~
+ <anon>:4:14: 4:18 error: cannot borrow `x[..]` as mutable more than once at a time
+ <anon>:4 let b = &mut x[1];
+ ^~~~
+ <anon>:3:14: 3:18 note: previous borrow of `x[..]` occurs here; the mutable borrow prevents subsequent moves, borrows, or modification of `x[..]` until the borrow ends
+ <anon>:3 let a = &mut x[0];
+ ^~~~
+ <anon>:6:2: 6:2 note: previous borrow ends here
+ <anon>:1 fn main() {
+ <anon>:2 let mut x = [1, 2, 3];
+ <anon>:3 let a = &mut x[0];
+ <anon>:4 let b = &mut x[1];
+ <anon>:5 println!("{} {}", a, b);
+ <anon>:6 }
+ ^
error: aborting due to 2 previous errors
```
In order to "teach" borrowck that what we're doing is ok, we need to drop down
to unsafe code. For instance, mutable slices expose a `split_at_mut` function
-that consumes the slice and returns *two* mutable slices. One for everything to
+that consumes the slice and returns two mutable slices. One for everything to
the left of the index, and one for everything to the right. Intuitively we know
this is safe because the slices don't overlap, and therefore alias. However
the implementation requires some unsafety:
references to the same object!
However it actually *does* work, exactly because iterators are one-shot objects.
-Everything an IterMut yields will be yielded *at most* once, so we don't
-*actually* ever yield multiple mutable references to the same piece of data.
+Everything an IterMut yields will be yielded at most once, so we don't
+actually ever yield multiple mutable references to the same piece of data.
-Perhaps surprisingly, mutable iterators *don't* require unsafe code to be
+Perhaps surprisingly, mutable iterators don't require unsafe code to be
implemented for many types!
For instance here's a singly linked list: