Add is not type constraint (different from is not pattern) [breaking change!] #4533
Unanswered
seanblue
asked this question in
Language Ideas
Replies: 1 comment 2 replies
-
Seems like you can force it with: if (o is not SomeType _) But it does feel weird that |
Beta Was this translation helpful? Give feedback.
2 replies
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
-
See this topic for full details and previous discussion: dotnet/roslyn#50671
Since you can read the full discussion in the other github issue, here's a summary:
is
can currently be two things: a type check and a pattern. On the other hand,is not
can only be a pattern. In theory you would think this shouldn't matter, but it actually results in odd situations where there is inconsistent behavior. I brought it up in the above issue as a bug, but I was told it was implemented correctly to the spec, so this discussion is to consider changing the spec to include anis not
type operator instead of relying on theis not
pattern, so that it works consistently with theis
type operator.Here's what it boils down to though:
Demo here
Now that that long example is out of the way, here's what's going on. We're trying to check against the type, but because there is a const with the same name, the const is taking priority. (If it's something other than a const, it actually fails to compile, as detailed in the other github issue.) If there wasn't a const or other member with the type name in scope, it would properly check against the type. The main thing I take issue with is that
if (data is not SomeType)
doesn't work the same asif (data is SomeType)
. You should be able to invert a condition/block knowing that the behavior will perfectly match. In fact Visual Studio currently gives suggestions to invert conditions which could result in different or uncompilable code. If we add anis not
type operator to be the parallel to theis
type operator instead of relying on theis not
pattern, theseif
conditions would both check the type, even if a member with the same name was in scope.There is however, a major drawback to this proposal: It would be a breaking change. In cases where it doesn't compile (e.g. if you had a property with the same name as the type), no problem. But if you did have a const and were doing
if (data is not SomeType)
, it would change behavior from checking against the const to checking against the type. For what it's worth in the issue on the roslyn github, there were views that this behavior was unintended and that a breaking change would likely be acceptable in this case. That is, until they determined it was implemented to the spec and told me to move the discussion over here. The main use case here is when you have a property returning a type and the property has the same name as the type. I don't know how often this comes up, but I did encounter it, which is how I first found this oddity.I'm curious to here what others think about this issue.
Beta Was this translation helpful? Give feedback.
All reactions