dotnet / dotnet/csharplang

Allow `is not ... designator` as legal pattern. (VS 16.8, .NET 5)

Open
#3,369 10 comments 40 reactions 0 assignees View on GitHub
Implemented Needs ECMA Spec Proposal champion
Dominant language
C#
Stars
12.7k
Forks
1.1k
Avg merge
11h 1m
Merged PRs (30d)
3

Description

This is currently not allowed in the spec here:

https://github.com/dotnet/csharplang/pull/3361/files/57d6360bf1816d0951073bac4d63c472c8e837c9#diff-16c1afdbaec4b56df38c7089e3d8cf7d

> The addition of `or` and `not` patterns creates some interesting new problems around pattern variables and definite assignment. Since variables can normally be declared at most once, it would seem any pattern variable declared on one side of an `or` pattern would not be definitely assigned when the pattern matches. Similarly, a variable declared inside a `not` pattern would not be expected to be definitely assigned when the pattern matches. The simplest way to address this is to forbid declaring pattern variables in these contexts. However, this may be too restrictive. There are other approaches to consider.

> One scenario that is worth considering is this

> ``` csharp
> if (e is not int i) return;
> M(i); // is i definitely assigned here?
> ```

> This does not work today because, for an *is-pattern-expression*, the pattern variables are considered *definitely assigned* only where the *is-pattern-expression* is true ("definitely assigned when true").

As mentioned in that discussion this leads to an unfortunate inconsistency that i think will be confusing for users. Specifically, the following forms are allowed and can be interchanged when appropriate

```c#
if (e is int)
if (e is not int)

if (!(e is int))
if (!(e is not int))
```

However, this is not true the moment you have:

```c#
if (!(e is int i)
```

This cannot be converted to:

```c#
if (e is not int i)
```

The is unfortunate as this form reads very well, and remove unnecessary parentheses clutter. It also means that only some guards can easily become patterns, while otehrs are forced to still be a mix of patterns+expressions.

--

I will champion this.

Contributor guide

No contributing guide indexed for this repository

Research direction

Start with the linked C# language-spec discussion and the examples involving `is not` pattern variables and definite assignment. Review how the proposed form should relate to negated `is` expressions; done means the language-design question has a resolved specification and definite-assignment behavior.

Written by the indexing model from the issue text.

Assessment

Tech stack
csharp
Domain
compilers
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
32/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.