-
Notifications
You must be signed in to change notification settings - Fork 1.1k
Pattern matching with type annotations allows impossible cases #3144
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
Comments
Note that the warning produced by scalac is not an exhaustivity warning:
scalac (and dotc) will not complain for: sealed trait Foo
class Bar
class Test {
def shouldError(foo: Foo) = foo match {
case _: Bar => 1
}
} If |
@allanrenucci will your changes cause the sample you and I provided produce an error? I haven't poked around in dotty at all, but in general compilers should error whenever you have a situation where the type being matched on is not a super type of the case. |
Fix #3144: emit warnings for unchecked type patterns
@liufengyun I'd like this to be re-opened, since what was resolved was actually unrelated to what I was concerned about. My example was perhaps bad. @allanrenucci touched on what I was talking about. The below example compiles, but should error: sealed trait Foo
case class Bar(s: String)
def shouldError(foo: Foo): String =
foo match {
case bar: Bar => bar.s
} I'm so used to generalizing that I did an un-necessary generalization in my earlier example which confused the issue. |
Scalac accepts the code above, as Dotty does. @Jacoby6000 can you specify why you think it should error? |
Since |
No, you could have |
I agree if |
More complicated example: sealed trait Foo
trait Child extends Foo
case class Bar(s: String)
class Bla extends Bar("") with Child // This could be in a different file The only thing we know for sure is that |
Yes, it's unreachable, because the checker knows that However, the Dotty checker tries to save some cycles by avoiding checking redundancy of the first clause. I guess Scalac checker intentionally does that as well. The Dotty checker also avoids doing an intersection of the pattern with the scrutinee for performance reasons. We can revert the optimisations to generate more warnings, but maybe after we see a real-world example where it causes problems. |
I'm really confused about why there is so much discussion around this. The discussion I've read seems to be worrying about things which do not matter. Even in the situation that smarter specified, it should not matter. The match is specifically matching on a Foo. It should only check for Foo. It should not allow for matching on types which do not extend Foo. What is the usecase for such a thing? Why should it ever be allowed? It seems like if you ever want to do this, you're doing something wrong anyway. Ignoring dotty semantics and focusing on what's correct, the scenario @smarter mentioned (or any scenario) should not warrant the pattern matcher treating a concrete type as Any. The real world example where it causes problems, is anywhere people want type-safety in a pattern match. I'd argue that supporting this just because of the |
Scalac currently agrees with me: https://scastie.scala-lang.org/Jacoby6000/QrCM9aQ5QVKS5aDMn2r2Yw. Though, in my opinion this should be a type error rather than a warning. |
Scalac agrees with you for the same reasons described above. If you remove the |
Doesn't this mean that pattern matching on concrete types treats that type as Any? Isn't that wrong? |
I'm starting to understand that as long as the type system has covariance, as well as intersections between types, then this must be supported. I still think it's bad, but you do what you have to do. How about we throw away subtyping and variance and just use proper ADTs? 😃 |
A compromise would be to disallow |
I like that. To me that makes much more sense. |
Fix #3144: more aggressively check unreachability
Uh oh!
There was an error while loading. Please reload this page.
This should not compile:
Not even a warning is produced, as is.
The text was updated successfully, but these errors were encountered: