What to expect in C# 8.0

C# 8.0 is the next major release version of C#

C# 8.0 is the next major release version of C#. As the work is still in progress and the below list of features is not a complete list, but it will definitely give you an idea of what you will be getting from the next major release.

New Features in C# 8.0

  • Nullable Reference Types

This is one of the cool features that you will love to have in the new version of C#.

This feature will allow the developers to:

  1. Express whether a variable, parameter or result of a reference type is intended to be null or not.
  2. Provide warnings when such variables, parameters and results are not used according to that intent.

Till now, you cannot add null into ordinary reference types such as string. Now with this new feature, the developers will only get warnings, not errors.


string s = null; // Warning: Assignment of null to non-nullable reference type

But, if you really want to have null, then use a nullable reference type, such as string?


string? s = null;

A flow analysis tracks nullable reference variables and the compiler will analyze the flow of your code to see if a null value could make it to where you are using it.


void M(string? s)
{
   Console.WriteLine(s.Length); // Warning: Possible null reference exception

   if (s != null)
   {
       Console.WriteLine(s.Length); // Ok: You won't get here if s is null
   }
}

  • Recursive Patterns Matching

Pattern matching extensions for C# enable many of the benefits of algebraic data types and pattern matching from functional languages, but in a way that smoothly integrates with the feel of the underlying language.


IEnumerable GetEmployeesOnLeave()
{
    foreach (var e in Employees)
    {
      if (e is Employee { OnLeave: true, Name: string name }) yield return name;
    }
}

The pattern Employee { OnLeave: true, Name: string name }) checks that the Person is a Employee, then applies the constant pattern true to their OnLeave property to see if they’re on leave, and the pattern string name to their Name property to get their name (if non-null). Thus, if e is a Employee, is not on leave and has a non-null name, you will get the name of those employees.

  • Async Streams

Until now, C# has support for iterator methods and async methods, but no support for a method that is both an iterator and an async method. C# 8.0 is coming with this new feature by allowing for await to be used in a new form of async iterator, one that returns an IAsyncEnumerable or IAsyncEnumerator rather than an IEnumerable or IEnumerator, with IAsyncEnumerable consumable in a new await foreach


async Task GetBigResultAsync()
{
    var result = await GetResultAsync();
    if (result > 20) return result;
    else return -1;
}

What if you want to return a set or stream of results. With C# 8.0, you can achieve this


async IAsyncEnumerable GetBigResultsAsync()
{
   await foreach (var result in GetResultsAsync())
   {
      if (result > 20) yield return result;
    }
}

  • Ranges and Indices

This is another new feature of C# 8.0 which allows the developers to add a type Index, which can be used for indexing. We can create an int index that would count from the beginning or we can also add ^ operator that would count from the end.


Index i1 = 2; // number 2 from the beginning
Index i2 = ^3; // number 3 from the end

int[] a = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
Console.WriteLine($"{a[i1]}, {a[i2]}"); // "2, 7"

C# 8.0 is also coming with a Range type, that consists of 2 indexes – start and end. The expression can be written as x..y


var slice = a[i1..i2]; // { 2, 3, 4, 5, 6 }

Dependencies: Async streams, indexers and ranges all rely on new framework types that will be part of .NET Standard 2.1. The types required to use these features won’t be available if you target C# 8.0 to .NET Framework 4.8.

There are some others active features in proposal and in progress state as well. We can only wait for the final version to be released to see all the features.