Open alexmaco opened 3 years ago
I played around with your code and found a smaller minimal example (here's the playground):
fn main() {
match () { _ => true } && true;
}
However, this outputs a typechecking error rather than a syntax error:
error[E0308]: mismatched types
--> src/main.rs:2:5
|
2 | match () { _ => true } && true;
| ^^^^^^^^^^^^^^^^^^^^^^- help: consider using a semicolon here
| |
| expected `()`, found `bool`
error: aborting due to previous error
After discussing this issue with someone else, I realized that if you add the semicolon like it suggests, then the error goes away, because && true
is a double reference (i.e. &(&true)
).
(Interestingly, if you run match () { _ => () } && true
, it actually compiles and evaluates to true
. Even though this looks like a typechecking error because it seems to be doing () && true
, it is actually doing (); &(&true)
. Here's the playground.)
I think the same thing is happening in your example, where it is interpreting the &&
as a double reference. It seems to be parsing the &&
as part of a pattern, but then it outputs an error when it sees you are trying to put a match
expression inside of a pattern. If you do,
fn main() {
let (a, b, c) = (3, 4, 5);
let r: bool = match c {
_ => match a {
_ => true
} && d => false
};
}
Then the _ => match a { _ => true }
is interpreted as one match arm while the &&d => false
is interpreted as another match arm. But this does not typecheck because c
is not a double reference. However, if you replace match c
with match &&c
, then it does typecheck and outputs true
. Here's the playground.
Triage: no change.
I tried this code (reduced to minimal triggering case):
(Failing in playground)
Fails with the following error:
However, the following works as expected:
Given that the second example compiles, we should expect the first one to compile as well.
Meta
I've found this issues on all rust versions 1.54.0 to 1.57 nightly inclusive. It doesn't look like a regression, since the same code is rejected as far back as 1.30, just with a different error message.