On 2/7/12 4:23 PM, Graydon Hoare wrote:
On 2/7/2012 3:24 PM, Niko Matsakis wrote:
Hm. I am confused at the description of the "hole" in the type system.
I was under the impression that this was the distinction between
immutable values and immutably-rooted values (those contained within a
path-of-immutable-references). Am I misunderstanding?
I am talking about our type system as implemented. We treat immutable
fields as covariantly typed, meaning that {x:T1} <: {x:T2} if T1 <: T2.
This is sound so long as the field x is really immutable; but it is
not. Here is an example of where this leads to bad results:
type T = { f: @const int };
fn foo(&t: T, v: @const int) {
t = {f:v};
}
fn main() {
let h = @3; // note: h is immutable
let g = @mutable {f: @mutable 4};
#error["h=%? g=%?", h, g]; // prints "h=@3 g=@(@4)"
foo(*g, h); // after this point, g.f == h but with a new type
#error["h=%? g=%?", h, g]; // prints "h=@3 g=@(@3)"
*g.f = 5;
#error["h=%? g=%?", h, g]; // prints "h=@5 g=@(@5)"
}
You can construct similar examples using vectors or fn types. If we
were to make more use of subtyping, for example via refinement types
such as those proposed in #1679, there would be many more such examples
as well.
Niko
_______________________________________________
Rust-dev mailing list
[email protected]
https://mail.mozilla.org/listinfo/rust-dev