Am trying to understand and validate the following statement in "Programming Rust" book
Shared access is read-only access. Values borrowed by shared references are read-only. Across the lifetime of a shared reference, neither its referent, nor anything reachable from that referent can be changed by anything. .......
From what I've understood from this, if you have an object hierarchy (say a->b->c), then if you take a shared reference to one of the objects in the middle (say b), then anything below that object (b and c) is read-only as long as the shared reference is live. Is my understanding correct ?
I tried the following contrived example to understand this:
#[derive(Debug)]
struct Middle {
b:u32,
left:Leaf,
right:Leaf
}
#[derive(Debug)]
struct Leaf {
a:u32
}
#[derive(Debug)]
struct Root {
a:u32,
b:Middle
}
fn array() {
let mut v = [Root{a:20, b:Middle{b:30, left:Leaf{a:10}, right:Leaf{a:11}}},
Root{a:30, b:Middle{b:40, left:Leaf{a:20}, right:Leaf{a:21}}},
Root{a:40, b:Middle{b:50, left:Leaf{a:30}, right:Leaf{a:31}}},
Root{a:50, b:Middle{b:60, left:Leaf{a:40}, right:Leaf{a:41}}}];
let r = &v[0].b.right;
let m = &mut v[0].b.left;
//let m = &mut v[2]; //compiler error
println!("{}", r.a);
}
fn main() {
array();
}
This code compiles. However if the commented out part of this code is un-commented, it fails with:
error[E0502]: cannot borrow `v[_]` as mutable because it is also borrowed as immutable
--> src/main.rs:26:13
|
24 | let r = &v[0].b.right;
| ------------- immutable borrow occurs here
25 | //let m = &mut v[0].b.left;
26 | let m = &mut v[2]; //compiler error
| ^^^^^^^^^ mutable borrow occurs here
27 | println!("{:}", r.a);
| --- immutable borrow later used here
Does this mean not only the parts that can be reachable by the referent but the path leading up to the referent is also read-only ?