iX 12/2019
S. 68
Review
Programmierung

C#8.0: Änderungen bei Schnittstellen und Compiler

In aller Strenge

Holger Schwichtenberg

Wie üblich hat Microsoft der neuen C#-Version einige Sprach­erweiterungen spendiert. Und der Compiler soll nun auf Programmierfehlern beruhende Null-Referenz-Laufzeitfehler abstellen.

Nachdem 2017 C# 7.0 erschien, gab es erstmals Unterversionen der Programmiersprache (7.1, 7.2, 7.3) mit jeweils nur wenigen Änderungen. Die Hauptversion 8.0 hat Microsoft am 23.09.2019 zusammen mit .NET Core 3.0 und Visual Studio 2019, Version 16.3, veröffentlicht. Grundsätzlich kann man den 8.0-Compiler auch mit dem klassischen .NET Framework einsetzen. Aber – und das ist neu – dort stehen nicht alle neuen Sprachfeatures zur Verfügung, denn einige erfordern Klassen in der .NET-Klassenbibliothek, die im klassischen .NET Frame­work nicht existieren. Nur in .NET Core, aber nicht in .NET Framework verfügbar sind die in diesem Beitrag behandelten Themen „Standardimplementierungen in Schnittstellen“, „Range und Index“ sowie „asynchrone Streams“.

Microsoft betont, dass die Weiterentwicklung des klassischen .NET Framework abgeschlossen ist, sodass man nicht mehr damit rechnen darf, dass C# 8.0 und folgende Sprachversionen dort jemals vollständig laufen können [1]. C# 8.0 ist komplett nur auf .NET-Implementierungen verfügbar, die dem .NET-Standard 2.1 folgen. Einen Überblick über die .NET-Unterstützung gibt es unter ix.de/z2x7.

Der Compiler trägt die Versionsnummer 3.3. Die Redmonder hatten ihn im Jahr 2015 neu implementiert und dabei die Versionszählung wieder bei 1.0 begonnen. 3.3 ist in Visual Studio 2019 ab Version 16.3, dem .NET Core Software Development Kit ab Version 3.0 und dem Nuget-Paket „Microsoft.Net.Compilers“ enthalten (siehe ix.de/z2x7).

Schon im September 2017 hatte Micro­soft für C# 8.0 angekündigt, dass Referenz­typen nicht mehr automatisch „nullable“ sein sollen; also fähig, den Wert null anzunehmen. Will der Entwickler es dennoch, soll er es explizit deklarieren müssen. Nach einiger Diskussion hat man sich jedoch dazu entschlossen, diese Neuerung nicht zum Standard, sondern zu einer Option des Compilers zu machen.

Der Compiler bringt dafür drei neue optionale Kontexte mit, also Bereiche im Programmcode, in Codedateien und ganzen Projekten:

  • Nullable Warning Context: Der Compiler warnt vor dem Auftreten von Null-­Referenz-Laufzeitfehlern bei allen Zugriffen auf Variablen, bei denen möglich oder nicht sichergestellt ist, dass sie nicht null enthalten beziehungsweise der Null-Fall nicht abgefangen wird.
  • Nullable Annotation Context: Re­ferenztypen wie string und eigene Klassen sind im Standard nicht mehr „nullable“. Wenn Null-Werte explizit gewünscht sind, ist dies mit dem Fragezeichen bei der Typdeklaration anzuzeigen, zum Beispiel string? und Klasse?. Nicht erlaubt sind Nullable<string> und Nullable<Klasse> wie bei den Nullable Value Types.
  • Nullable Context: Allgemein wird so ein Kontext bezeichnet, der sowohl Warning Context als auch Annotation Context ist, also die Funktionen beider Kontexte in sich vereint.

Die Tabelle „Varianten des Null-Kontextes in C# 8.0“ stellt die drei Kontext­arten gegenüber. Das Aktivieren auf Projektebene ist möglich in .csproj-Dateien sowohl für das klassische .NET Framework als auch in den kompakteren .NET-Core-­Projektdateien. Listing 1 zeigt an Beispielen die Auswirkungen der drei Kontextarten.

Varianten des Null-Kontextes in C# 8.0
Nullable Annotation Context Nullable Warning Context Nullable Context (Annotation Context + Warning Context) 
Bedeutung der Deklaration Klasse  Non-Nullable Nullable Non-Nullable
Bedeutung der Deklaration Klasse?  Nullable nicht erlaubt (führt zur Warnung) Nullable
Warnung vor Null Reference Exceptions ein ja ja
Aktivierung auf Projektebene in der .csproj-Datei <Nullable>annotations</Nullable> <Nullable>warnings</Nullable> <Nullable>enable</Nullable>
Aktivierung im Code #nullable enable annotations #nullable enable warnings #nullable enable
Deaktivierung im Code #nullable disable annotations #nullable disable warnings #nullable disable
Zurücksetzung auf Projekteinstellung #nullable restore annotations #nullable restore warnings #nullable restore

Eine weitere Behandlung des Null-Falls ist hinzugekommen in Form des Operators „Null Coalescing Assignment“ ??=. Mit ihm kann der Entwickler eine Zuweisung ausführen, wenn eine Variable den Wert null hat. Statt

Kommentieren