Currently the following is allowed:
fn main() {
let x = 4;
let x = 5;
}
To me this breaks the, immutable by default, ideal of Rust
How so? You have a binding named 'x' that is 4, and you make a new binding (that happens to be called 'x' too) that is set to 5, it did not change the original x's value of 4, it is still 4, just shadowed at this point (but anything pointing to it after the second binding still gets the original value of 4).
Yes the original value is there and it is shadowed but it is for that reason that I don't think that this should be allowed (in the same context) since using x now has a different value
This is an established and commonly used pattern in the Rust ecosystem, particularly when changing the type of a bit of data:
let x = "5.3";
let x = x.parse::<f32>().unwrap();
Why is that good design for a type strict language?
There are already some clippy lints for this: shadow_reuse, shadow_same and shadow_unrelated.
It avoids needing to make a bunch of different names for the same thing. What are the concrete issues with this approach?
Also it makes it really clear at the second let x that you don't need the original x anymore. So there's some object lifetime information there that you'd otherwise need to encode with scopes or couldn't encode at all.
@sfackler Shadowing makes it possible to accidentally give two distinct values the same name, without realizing. I don't think it's common, but it has happened to me once or twice. Not that I care, just giving an example. :)
Most helpful comment
It avoids needing to make a bunch of different names for the same thing. What are the concrete issues with this approach?