-
Notifications
You must be signed in to change notification settings - Fork 12.9k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Coercion sites are not consistent between struct tuples and structs #31260
Comments
This coercion is important when using |
Because of rust-lang/rust#31260, a cast must be inserted explicitly instead of letting rustc implicitly coercing the type.
The tuple struct case is actually the function call "expected type" propagation, which would have to be adapted to struct literals as well. |
Yes. |
Coercion already happens in non-generic struct literals: struct Foo { s: &'static [u8] }
static FOO: Foo = Foo { s: b"foo" }; |
@SimonSapin Yes, but the field types are taken from the struct and not combined with the overall expected type for the struct literal. |
Because of rust-lang/rust#31260, a cast must be inserted explicitly instead of letting rustc implicitly coercing the type.
I just discovered this bug/unexpected behavior today (#34240). I would like to see some movement on it because it's surprising that these two don't work the same way. Here's a workaround I found; it's ugly as hell but I'm using it in a generated file that no human would want to look through anyway: https://is.gd/boA5ut I tried type ascription but it seems to not cue coercion, it just moves the type error: https://is.gd/yut0EK It seems that forcing a concrete type on the struct literal works as well (I didn't expect this syntax to work, honestly): https://is.gd/ZipLo1 Unfortunately this won't work for me because I'm using |
Any news on this? |
Is anyone working on it? |
Propagate expected type hints through struct literals. Partial fix for rust-lang#31260 to maximize backwards-compatibility, i.e. the hint is provided but not coerced to. The added test works because `{...; x}` with a hint of `T` coerces `x` to `T`, and the reasoning why that is slightly different has to do with DSTs: `&Struct { tail: [x] }: &Struct<[T]>` has a hint of `[T]` for `[x]`, but the inferred type should be `[T; 1]` to succeed later, so `[x]` shouldn't be *forced* to be `[T]`. *However*, implementing that complete behavior in a backwards-compatible way may be non-trivial, and has not yet been fully investigated, while this PR fixes rust-lang#40355 and can be backported. r? @nikomatsakis
Propagate expected type hints through struct literals. Partial fix for rust-lang#31260 to maximize backwards-compatibility, i.e. the hint is provided but not coerced to. The added test works because `{...; x}` with a hint of `T` coerces `x` to `T`, and the reasoning why that is slightly different has to do with DSTs: `&Struct { tail: [x] }: &Struct<[T]>` has a hint of `[T]` for `[x]`, but the inferred type should be `[T; 1]` to succeed later, so `[x]` shouldn't be *forced* to be `[T]`. *However*, implementing that complete behavior in a backwards-compatible way may be non-trivial, and has not yet been fully investigated, while this PR fixes rust-lang#40355 and can be backported. r? @nikomatsakis
Propagate expected type hints through struct literals. Partial fix for rust-lang#31260 to maximize backwards-compatibility, i.e. the hint is provided but not coerced to. The added test works because `{...; x}` with a hint of `T` coerces `x` to `T`, and the reasoning why that is slightly different has to do with DSTs: `&Struct { tail: [x] }: &Struct<[T]>` has a hint of `[T]` for `[x]`, but the inferred type should be `[T; 1]` to succeed later, so `[x]` shouldn't be *forced* to be `[T]`. *However*, implementing that complete behavior in a backwards-compatible way may be non-trivial, and has not yet been fully investigated, while this PR fixes rust-lang#40355 and can be backported. r? @nikomatsakis
Propagate expected type hints through struct literals. Partial fix for rust-lang#31260 to maximize backwards-compatibility, i.e. the hint is provided but not coerced to. The added test works because `{...; x}` with a hint of `T` coerces `x` to `T`, and the reasoning why that is slightly different has to do with DSTs: `&Struct { tail: [x] }: &Struct<[T]>` has a hint of `[T]` for `[x]`, but the inferred type should be `[T; 1]` to succeed later, so `[x]` shouldn't be *forced* to be `[T]`. *However*, implementing that complete behavior in a backwards-compatible way may be non-trivial, and has not yet been fully investigated, while this PR fixes rust-lang#40355 and can be backported. r? @nikomatsakis
Propagate expected type hints through struct literals. Partial fix for rust-lang#31260 to maximize backwards-compatibility, i.e. the hint is provided but not coerced to. The added test works because `{...; x}` with a hint of `T` coerces `x` to `T`, and the reasoning why that is slightly different has to do with DSTs: `&Struct { tail: [x] }: &Struct<[T]>` has a hint of `[T]` for `[x]`, but the inferred type should be `[T; 1]` to succeed later, so `[x]` shouldn't be *forced* to be `[T]`. *However*, implementing that complete behavior in a backwards-compatible way may be non-trivial, and has not yet been fully investigated, while this PR fixes rust-lang#40355 and can be backported. r? @nikomatsakis
Making sure we remember to look at this. |
@nikomatsakis What I did is I computed a "light hint" (which becomes "strong hint", i.e. forcing coercion, if it reaches a block, and it's enough to help integer inference for #40355). This is a common problem with coercion hints, in that unless there's enough type information to prevent them from triggering, they will trigger early even if that breaks later on. The thing to try here is to replace these two lines with the simpler: self.check_expr_coercable_to_type(&field.expr, field_type_hint)
|
@eddyb ok, I was mostly wondering if you encountered actual regressions in practice, or just theorize that this might lead to problems. |
@nikomatsakis I don't think I got the chance to do a crater run and then I lost track of it. |
@arielb1 will open a PR and we can try a crater run at least. |
Fully fixes rust-lang#31260. This needs a crater run.
Coerce fields to the expected field type Fully fixes #31260. This needs a crater run. I was supposed to do this last month but it slipped. Let's get this done.
There is still a similar problem with the type inference of temporaries when you have an array that should be interpreted as a slice buried in a tuple inside an outer slice. |
STRUCT
fails to type check, whileTUPLE
succeeds.The text was updated successfully, but these errors were encountered: