Nullwerte zulassende Verweistypen
In einem Kontext ohne Beachtung von Nullable-Eigenschaften lassen alle Verweistypen Nullwerte zu. Als Nullable-Verweistypen wird eine Reihe von Features bezeichnet, die in einem Nullable-fähigen Kontext aktiviert werden und die die Wahrscheinlichkeit minimieren, dass Ihr Code zur Laufzeit System.NullReferenceException auslöst. Nullwerte zulassende Verweistypen enthalten drei Features, mit denen Sie diese Ausnahmen vermeiden können (einschließlich der Möglichkeit, einen Verweistyp explizit als Nullwerte zulassend zu kennzeichnen):
- Verbesserte statische Flussanalyse, die bestimmt, ob eine Variable
null
sein kann, bevor sie dereferenziert wird. - Attribute, die APIs mit Anmerkungen kommentieren, sodass die Flussanalyse den NULL-Status bestimmt.
- Variablenanmerkungen, die Entwickler verwenden, um den beabsichtigten NULL-Zustand für eine Variable explizit zu deklarieren.
Nullzustandsanalyse und Variablenanmerkungen sind für vorhandene Projekte standardmäßig deaktiviert. Dies bedeutet, dass alle Verweistypen weiterhin Nullwerte zulassen. Ab .NET 6 sind sie standardmäßig für neue Projekte aktiviert. Informationen zum Aktivieren dieser Features durch Deklarieren eines Nullable-Anmerkungskontexts finden Sie unter Nullable-Kontexte.
Im restlichen Teil dieses Artikels wird beschrieben, wie diese drei Featurebereiche funktionieren, um Warnungen zu generieren, wenn Ihr Code möglicherweise einen null
-Wert dereferenziert. Das Dereferenzieren einer Variablen bedeutet, mithilfe des .
-Operators (Punkt) auf einen ihrer Member zuzugreifen, wie im folgenden Beispiel gezeigt:
string message = "Hello, World!";
int length = message.Length; // dereferencing "message"
Wenn Sie eine Variable dereferenzieren, deren Wert null
ist, löst die Laufzeit eine System.NullReferenceException aus.
Sie können diese Konzepte auch in unserem Lernmodul zur Nullsicherheit in C# erkunden.
Analyse des NULL-Status
Bei der Nullzustandsanalyse wird der Nullzustand von Verweisen nachverfolgt. Diese statische Analyse gibt Warnungen aus, wenn Ihr Code möglicherweise null
dereferenziert. Sie können diese Warnungen behandeln, um die Fälle zu minimieren, in denen die Laufzeit eine System.NullReferenceException auslöst. Der Compiler verwendet statische Analyse, um den NULL-Status einer Variablen zu bestimmen. Eine Variable ist entweder not-null oder maybe-null. Der Compiler bestimmt auf zwei Arten, dass eine Variable nicht not-null ist:
- Die Variable wurde einem Wert zugewiesen, der bekanntermaßen ungleich NULL ist.
- Die Variable wurde mit
null
überprüft und seit dieser Überprüfung nicht mehr geändert.
Jede Variable, die der Compiler nicht als not-null bestimmt hat, wird als maybe-null betrachtet. Die Analyse liefert Warnungen in Situationen, in denen Sie einen null
-Wert versehentlich dereferenzieren können. Der Compiler generiert Warnungen basierend auf dem NULL-Status.
- Wenn eine Variable not-null ist, kann diese Variable sicher dereferenziert werden.
- Wenn eine Variable maybe-null ist, muss diese Variable überprüft werden, um sicherzustellen, dass sie vor der Deferenzierung nicht
null
ist.
Betrachten Sie das folgenden Beispiel:
string message = null;
// warning: dereference null.
Console.WriteLine($"The length of the message is {message.Length}");
var originalMessage = message;
message = "Hello, World!";
// No warning. Analysis determined "message" is not null.
Console.WriteLine($"The length of the message is {message.Length}");
// warning!
Console.WriteLine(originalMessage.Length);
Im vorherigen Beispiel bestimmt der Compiler, dass message
maybe-null ist, wenn die erste Meldung ausgegeben wird. Für die zweite Meldung wird keine Warnung angezeigt. Die letzte Codezeile generiert eine Warnung, weil originalMessage
möglicherweise NULL ist. Das folgende Beispiel zeigt eine praktischere Verwendung, um eine Struktur von Knoten bis zum Stamm zu durchlaufen und jeden Knoten während des Durchlaufs zu verarbeiten:
void FindRoot(Node node, Action<Node> processNode)
{
for (var current = node; current != null; current = current.Parent)
{
processNode(current);
}
}
Der Code oben generiert keine Warnungen zum Dereferenzieren der Variablen current
. Die statische Analyse bestimmt, dass current
nie dereferenziert wird, wenn der Wert maybe-null ist. Die Variable current
wird anhand von null
überprüft, bevor auf current.Parent
zugegriffen und current
an die Aktion ProcessNode
übergeben wird. Die vorherigen Beispiele zeigen, wie der Compiler den NULL-Status für lokale Variablen bestimmt, wenn initialisiert, zugewiesen oder mit null
verglichen wird.
Die Nullzustandsanalyse führt keine Ablaufverfolgung in aufgerufene Methoden durch. Daher generieren Felder, die in einer gemeinsamen, von Konstruktoren aufgerufenen Hilfsmethode initialisiert werden, eine Warnung mit der folgenden Vorlage:
Die Non-Nullable-Eigenschaft Name muss beim Beenden des Konstruktors einen Wert ungleich NULL enthalten.
Es gibt zwei Möglichkeiten zur Lösung dieser Warnungen: Konstruktorverkettung oder Nullable-Attribute für die Hilfsmethode. Im folgenden Code ist ein Beispiel für jede Methode dargestellt. Die Person
-Klasse verwendet einen gemeinsamen Konstruktor, der von allen anderen Konstruktoren aufgerufen wird. Die Student
-Klasse verfügt über eine Hilfsmethode, die mit dem System.Diagnostics.CodeAnalysis.MemberNotNullAttribute-Attribut als Anmerkung versehen ist:
using System.Diagnostics.CodeAnalysis;
public class Person
{
public string FirstName { get; set; }
public string LastName { get; set; }
public Person(string firstName, string lastName)
{
FirstName = firstName;
LastName = lastName;
}
public Person() : this("John", "Doe") { }
}
public class Student : Person
{
public string Major { get; set; }
public Student(string firstName, string lastName, string major)
: base(firstName, lastName)
{
SetMajor(major);
}
public Student(string firstName, string lastName) :
base(firstName, lastName)
{
SetMajor();
}
public Student()
{
SetMajor();
}
[MemberNotNull(nameof(Major))]
private void SetMajor(string? major = default)
{
Major = major ?? "Undeclared";
}
}
Hinweis
In C# 10 wurde die eindeutige Zuweisung und die Analyse des NULL-Status verbessert. Wenn Sie ein Upgrade auf C# 10 durchführen, werden möglicherweise weniger Nullable-Warnungen angezeigt, die falsch positiv sind. Weitere Informationen zu den Verbesserungen finden Sie in der Featurespezifikation für Verbesserungen an der eindeutigen Zuweisung.
Die Nullable-Zustandsanalyse und die vom Compiler generierten Warnungen helfen Ihnen, Programmfehler durch Dereferenzierung von null
zu vermeiden. Im Artikel Auflösen von Nullable-Warnungen werden Techniken zum Korrigieren der Warnungen vorgestellt, die wahrscheinlich in Ihrem Code angezeigt werden.
Attribute für API-Signaturen
Die NULL-Statusanalyse benötigt Hinweise von Entwicklern, um die Semantik von APIs zu verstehen. Einige APIs bieten NULL-Überprüfungen und sollten den null-state einer Variablen von maybe-null in not-null ändern. Andere APIs geben Ausdrücke zurück, die not-null oder maybe-null sind, je nach dem null-state der Eingabeargumente. Sehen Sie sich beispielsweise den folgenden Code an, der eine Meldung anzeigt:
public void PrintMessage(string message)
{
if (!string.IsNullOrWhiteSpace(message))
{
Console.WriteLine($"{DateTime.Now}: {message}");
}
}
Basierend auf der Überprüfung würde jeder Entwickler diesen Code als sicher betrachten, und er sollte keine Warnungen generieren. Der Compiler weiß nicht, dass IsNullOrWhiteSpace
eine NULL-Überprüfung bereitstellt. Wenn IsNullOrWhitespace
false,
zurückgibt, ist der NULL-Zustand der Zeichenfolge nicht NULL. Wenn IsNullOrWhitespace
true
zurückgibt, wird der NULL-Zustand nicht geändert. Im vorherigen Beispiel enthält die Signatur NotNullWhen
, um den NULL-Status von message
anzugeben:
public static bool IsNullOrWhiteSpace([NotNullWhen(false)] string message);
Attribute bieten ausführliche Informationen zum NULL-Status von Argumenten, Rückgabewerten und Membern der Objektinstanz, die zum Aufrufen eines Members verwendet werden. Die Details zu den einzelnen Attributen finden Sie im Sprachreferenzartikel zu Nullable-Verweisattributen. Alle .NET-Runtime-APIs wurden in .NET 5 mit Anmerkungen kommentiert. Sie verbessern die statische Analyse, indem Sie Ihre APIs kommentieren, um semantische Informationen zum null-state von Argumenten und Rückgabewerten zu liefern.
Nullable-Variablenanmerkungen
Die null-state-Analyse bietet stabile Analysen für die meisten Variablen. Der Compiler benötigt weitere Informationen von Ihnen für Membervariablen. Der Compiler kann keine Annahmen über die Reihenfolge treffen, in der auf öffentliche Member zugegriffen wird. Auf alle öffentlichen Member könnte in beliebiger Reihenfolge zugegriffen werden. Jeder der zugreifbaren Konstruktoren kann verwendet werden, um das Objekt zu initialisieren. Wenn ein Memberfeld jemals auf null
festgelegt werden kann, muss der Compiler davon ausgehen, dass sein null-status zu Beginn jeder Methode maybe-null ist.
Sie verwenden Anmerkungen, die deklarieren können, ob eine Variable ein Nullable-Verweistyp oder ein Nicht-Nullable-Verweistyp ist. Diese Anmerkungen enthalten wichtige Anweisungen zum null-state für Variablen:
- Ein Verweis darf nicht NULL sein. Der Standardstatus einer keine Nullwerte zulassenden Verweisvariable ist nicht-null. Der Compiler erzwingt Regeln, die sicherstellen, dass das Dereferenzieren dieser Variablen sicher ist, ohne zuerst zu überprüfen, ob sie nicht NULL sind:
- Die Variable muss mit einem Wert ungleich NULL initialisiert werden.
- Der Variablen kann nie der Wert
null
zugewiesen werden. Der Compiler gibt eine Warnung aus, wenn der Code einen maybe-null-Ausdruck einer Variablen zuweist, die nicht NULL sein sollte.
- Ein Verweis darf NULL sein. Der Standardstatus einer Nullwerte zulassenden Verweisvariable ist maybe-null. Der Compiler erzwingt Regeln, um sicherzustellen, dass Sie ordnungsgemäß auf einen
null
-Verweis überprüft haben:- Die Variable kann nur dereferenziert werden, wenn der Compiler garantieren kann, dass der Wert nicht
null
ist. - Diese Variablen können mit dem Standardwert
null
initialisiert und in anderem Code dem Wertnull
zugewiesen werden. - Der Compiler gibt keine Warnungen aus, wenn Code einer Variablen, die NULL sein kann, einen maybe-null-Ausdruck zuweist.
- Die Variable kann nur dereferenziert werden, wenn der Compiler garantieren kann, dass der Wert nicht
Jede Verweisvariable, die nicht null
sein soll, weist den null-statenot-null auf. Jede Verweisvariable, die anfänglich null
sein kann, hat den null-statemaybe-null.
Ein Nullable-Verweistyp wird mithilfe der gleichen Syntax wie Nullable-Werttypen aufgeführt: Ein ?
wird an den Variablentyp angefügt. Beispielsweise stellt die folgende Variablendeklaration eine Nullable-Zeichenfolgenvariable, name
, dar:
string? name;
Bei jeder Variable, bei der ?
nicht an den Typnamen angefügt ist, handelt es sich um einen Non-Nullable-Verweistyp. Dies umfasst alle Verweistypvariablen in vorhandenem Code, wenn Sie dieses Feature aktiviert haben. Alle implizit typisierten lokalen Variablen (die mit var
deklariert wurden) sind Nullable-Verweistypen. Wie in den vorherigen Abschnitten gezeigt, bestimmt die statische Analyse den null-state lokaler Variablen, um zu ermitteln, ob sie maybe-null sind.
Manchmal müssen Sie eine Warnung überschreiben, wenn Sie wissen, dass eine Variable nicht NULL ist, der Compiler aber bestimmt, dass der null-statemaybe-null ist. Sie verwenden den NULL-toleranten Operator!
nach einem Variablennamen, um einen Nullzustandungleich NULL zu erzwingen. Wenn Sie beispielsweise wissen, dass die Variable name
nicht null
ist, der Compiler aber eine Warnung ausgibt, können Sie folgenden Code schreiben, um die Analyse des Compilers zu überschreiben:
name!.Length;
Nullable-Verweistypen und Nullable-Werttypen bieten ein ähnliches semantisches Konzept: Eine Variable kann einen Wert oder ein Objekt darstellen, oder diese Variable kann null
sein. Nullable-Verweistypen und Nullable-Werttypen werden jedoch unterschiedlich implementiert: Nullable-Werttypen werden mit System.Nullable<T> implementiert, und Nullable-Verweistypen werden durch Attribute implementiert, die vom Compiler gelesen werden. string?
und string
werden z. B. beide durch den gleichen Typ dargestellt: System.String. int?
und int
werden jedoch durch System.Nullable<System.Int32>
bzw. System.Int32 dargestellt.
Nullable-Verweistypen sind ein Kompilierzeitfeature. Dies bedeutet, dass Aufrufer Warnungen ignorieren und bewusst null
als Argument für eine Methode verwenden können, die einen Non-Nullable-Verweis erwartet. Autoren von Bibliotheken sollten Laufzeitüberprüfungen auf NULL-Argumentwerte integrieren. ArgumentNullException.ThrowIfNull ist die bevorzugte Option zur Laufzeitüberprüfung eines Parameters auf NULL.
Wichtig
Das Aktivieren von Nullable-Anmerkungen kann die Art und Weise ändern, mit der Entity Framework Core bestimmt, ob ein Datenmember erforderlich ist. Weitere Einzelheiten finden Sie im Artikel Entity Framework Core-Grundlagen: Arbeiten mit Nullable-Verweistypen.
Generics
Generics erfordern detaillierte Regeln zur Behandlung von T?
für jeden Typparameter T
. Die Regeln sind aufgrund des bisherigen Verlaufs und der unterschiedlichen Implementierung für einen Nullwerte zulassende Werttyp und einen Nullwerte zulassende Verweistyp notwendigerweise ausführlich. Nullwerte zulassende Werttypen werden mit der Struktur System.Nullable<T> implementiert. Nullwerte zulassende Verweistypen werden als Typ-Anmerkungen implementiert, die dem Compiler semantische Regeln vorgeben.
- Wenn das Typargument für
T
ein Verweistyp ist, verweistT?
auf den entsprechenden Nullwerte zulassenden Verweistyp. Wenn zum BeispielT
einstring
ist, dann istT?
einstring?
. - Wenn das Typargument für
T
ein Wertetyp ist, verweistT?
auf denselben Wertetyp,T
. Wenn zum BeispielT
einint
ist, ist auchT?
einint
. - Wenn das Typargument für
T
ein löschbarer Verweistyp ist, verweistT?
auf denselben löschbaren Verweistyp. Wenn zum BeispielT
einstring?
ist, dann istT?
auch einstring?
. - Wenn das Typargument für
T
ein löschbarer Werttyp ist, verweistT?
auf denselben löschbaren Werttyp. Wenn zum BeispielT
einint?
ist, dann istT?
auch einint?
.
Bei Rückgabewerten ist T?
äquivalent zu [MaybeNull]T
; für Argumentwerte ist T?
äquivalent zu [AllowNull]T
. Weitere Informationen finden Sie im Artikel Attribute für die Nullzustandsanalyse in der Sprachreferenz.
Mit Einschränkungen können Sie ein anderes Verhalten festlegen:
- Die
class
-Einschränkung bedeutet, dassT
ein keine Nullwerte zulassender Verweistyp sein muss (z. B.string
). Der Compiler gibt eine Warnung aus, wenn Sie einen Nullwerte zulassenden Verweistyp verwenden, z. B.string?
fürT
. - Die
class?
-Einschränkung bedeutet, dassT
ein Verweistyp sein muss, entweder ein keine Nullwerte zulassender (string
) oder ein Nullwerte zulassender Verweistyp (z. B.string?
). Wenn der Typparameter ein löschbarer Verweistyp ist, z. B.string?
, verweist ein Ausdruck vonT?
auf denselben löschbaren Verweistyp, z. B.string?
. - Die
notnull
-Einschränkung bedeutet, dassT
ein Non-Nullable-Verweistyp oder ein Non-Nullable-Werttyp sein muss. Wenn Sie einen Nullwerte zulassende Verweistyp oder einen Nullwerte zulassende Werttyp für den Typparameter verwenden, generiert der Compiler eine Warnung. WennT
ein Werttyp ist, ist der Rückgabewert dieser Werttyp und nicht der entsprechende löschbare Werttyp.
Diese Einschränkungen helfen dem Compiler, weitere Informationen zur Verwendung von T
zu erhalten. Dies hilft, wenn Entwickler den Typ für T
auswählen, und bietet eine bessere null-state-Analyse, wenn eine Instanz des generischen Typs verwendet wird.
Nullable-Kontexte
Die neuen Features, die vor dem Auslösen von System.NullReferenceException schützen, können störend sein, wenn sie in einer vorhandenen Codebasis aktiviert werden:
- Alle explizit typisierten Verweisvariablen werden als Non-Nullable-Verweistypen interpretiert.
- Die Bedeutung der
class
-Einschränkung in Generika wurde geändert, um einen Non-Nullable-Verweistyp anzugeben. - Aufgrund dieser neuen Regeln werden neue Warnungen generiert.
Sie müssen sich ausdrücklich für die Nutzung dieser Funktionen in Ihren bestehenden Projekten entscheiden. Dies bietet einen Migrationspfad und bewahrt Abwärtskompatibilität. Nullable-Kontexte ermöglichen eine differenzierte Steuerung der Interpretation von Verweistypvariablen durch den Compiler. Der Nullable-Anmerkungskontext bestimmt das Verhalten des Compilers. Es gibt vier Werte für den Nullable-Anmerkungskontext:
- disable: Es handelt sich um Code ohne Nullable-Beachtung.
- Nullable-Warnungen sind deaktiviert.
- Alle Verweistypvariablen sind Nullable-Verweistypen.
- Sie können eine Variable nicht als Nullable-Verweistyp deklarieren, indem Sie das Suffix
?
für den Typ verwenden. - Sie können den NULL-toleranten Operator (
!
) verwenden, das hat aber keine Auswirkungen.
- enabled: Der Compiler aktiviert alle Features für die Nullverweisanalyse sowie alle Sprachfeatures.
- Alle neuen Nullable-Warnungen sind aktiviert.
- Sie können das Suffix
?
verwenden, um einen Nullable-Verweistyp zu deklarieren. - Alle anderen Verweistypvariablen sind Non-Nullable-Verweistypen.
- Der NULL-tolerante Operator unterdrückt Warnungen für eine mögliche Zuweisung zu
null
.
- warnings: Der Compiler führt alle NULL-Analysen durch und gibt Warnungen aus, wenn Code möglicherweise
null
dereferenziert.- Alle neuen Nullable-Warnungen sind aktiviert.
- Verwenden Sie das Suffix
?
verwenden, um einen Nullable-Verweistyp zu deklarieren, der eine Warnung generiert. - Alle Verweistypvariablen dürfen NULL sein. Member haben jedoch den null-statenot-null an der öffnenden geschweiften Klammer aller Methoden, es sei denn, sie werden mit dem Suffix
?
deklariert. - Sie können den NULL-toleranten Operator (
!
) verwenden.
- annotations: Der Compiler führt keine NULL-Analyse durch oder gibt Warnungen aus, wenn Code möglicherweise
null
dereferenziert.- Alle neuen Nullable-Warnungen sind deaktiviert.
- Sie können das Suffix
?
verwenden, um einen Nullable-Verweistyp zu deklarieren. - Alle anderen Verweistypvariablen sind Non-Nullable-Verweistypen.
- Sie können den NULL-toleranten Operator (
!
) verwenden, das hat aber keine Auswirkungen.
Der Nullable-Anmerkungskontext und der Nullable-Warnungskontext können für ein Projekt festgelegt werden, indem Sie das <Nullable>
-Element in Ihrer .csproj-Datei verwenden. Dieses Element konfiguriert, wie der Compiler die NULL-Zulässigkeit von Typen interpretiert und welche Warnungen ausgegeben werden. In der folgenden Tabelle sind die zulässigen Werte aufgeführt und die von ihnen angegebenen Kontexte zusammengefasst.
Kontext | Dereferenzierungswarnungen | Zuweisungswarnungen | Verweistypen | ? -Suffix |
! -Operator |
---|---|---|---|---|---|
disable |
Disabled | Disabled | Alle lassen Nullwerte zu. | Kann nicht verwendet werden. | Hat keine Auswirkungen. |
enable |
Aktiviert | Aktiviert | Non-nullable, es sei denn, es wurde mit ? deklariert |
Deklariert einen Nullable-Typ | Unterdrückt Warnungen für mögliche null -Zuweisungen. |
warnings |
Aktiviert | Nicht verfügbar | Alle lassen Nullwerte zu, aber Member werden bei öffnenden geschweiften Klammern von Methoden als nicht NULL betrachtet. | Erzeugt eine Warnung | Unterdrückt Warnungen für mögliche null -Zuweisungen. |
annotations |
Disabled | Disabled | Non-nullable, es sei denn, es wurde mit ? deklariert |
Deklariert einen Nullable-Typ | Hat keine Auswirkungen. |
Für Verweistypvariablen in Code, der in einem disable-Kontext kompiliert wurde, erfolgt keine Nullable-Beachtung. Sie können ein null
-Literal oder eine maybe-null-Variable einer Variablen zuweisen, die Nullwerte zulassend-nicht beachtend ist. Der Standardzustand einer Variable mit der Eigenschaft Nullwerte zulassend-nicht beachtend ist jedoch nicht-null.
Sie können auswählen, welche Einstellung für Ihr Projekt am besten geeignet ist:
- Wählen Sie disable für Legacyprojekte, die Sie nicht aufgrund von Diagnosen oder neuen Features aktualisieren möchten.
- Wählen Sie warnings aus, um zu bestimmen, wo Ihr Code möglicherweise System.NullReferenceExceptions auslösen kann. Sie können diese Warnungen beheben, bevor Sie den Code ändern, um Non-Nullable-Verweistypen zu aktivieren.
- Wählen Sie annotations aus, um Ihre Entwurfsabsicht auszudrücken, bevor Sie Warnungen aktivieren.
- Wählen Sie enable für neue Projekte und aktive Projekte, die Sie vor NULL-Verweisausnahmen schützen möchten.
Beispiel:
<Nullable>enable</Nullable>
Sie können auch Anweisungen verwenden, um diese gleichen Kontexte an beliebiger Stelle in Ihrem Quellcode festzulegen. Diese sind besonders nützlich, wenn Sie eine große Codebasis migrieren.
#nullable enable
: Legt den Nullable-Anmerkungskontext und den Nullable-Warnungskontext auf enable fest.#nullable disable
: Legt den Nullable-Anmerkungskontext und den Nullable-Warnungskontext auf disable fest.#nullable restore
: Stellt die Projekteinstellungen für den Nullable-Anmerkungskontext und den Nullable-Warnungskontext wieder her.#nullable disable warnings
: Legt den Nullable-Warnungskontext auf disable fest.#nullable enable warnings
: Legt den Nullable-Warnungskontext auf enable fest.#nullable restore warnings
: Stellt die Projekteinstellungen für den Nullable-Warnungskontext wieder her.#nullable disable annotations
: Legt den Nullable-Anmerkungskontext auf disable fest.#nullable enable annotations
: Legt den Nullable-Anmerkungskontext auf enable fest.#nullable restore annotations
: Stellt die Projekteinstellungen für den Anmerkungswarnungskontext wieder her.
Für jede Codezeile können Sie eine der folgenden Kombinationen festlegen:
Warnungskontext | Anmerkungskontext | Zweck |
---|---|---|
Standardeinstellung des Projekts | Standardeinstellung des Projekts | Standard |
enable | disable | Analysewarnungen korrigieren |
enable | Standardeinstellung des Projekts | Analysewarnungen korrigieren |
Standardeinstellung des Projekts | enable | Typanmerkungen hinzufügen |
enable | enable | Bereits migrierter Code |
disable | enable | Kommentieren von Code vor dem Beheben von Warnungen |
disable | disable | Hinzufügen von Legacycode zum migrierten Projekt |
Standardeinstellung des Projekts | disable | Selten |
disable | Standardeinstellung des Projekts | Selten |
Mit diesen neun Kombinationen können Sie die Diagnosen, die der Compiler für Ihren Code ausgibt, detailliert steuern. Sie können weitere Features in jedem Bereich aktivieren, den Sie aktualisieren, ohne zusätzliche Warnungen zu erhalten, die Sie noch nicht beheben möchten.
Wichtig
Der globale Nullable-Kontext gilt nicht für generierte Codedateien. Der Nullable-Kontext ist unabhängig von der Strategie für alle als generiert gekennzeichneten Quelldateien deaktiviert. Das bedeutet, dass alle in generierten Dateien enthaltenen APIs nicht mit Anmerkungen versehen werden. Es gibt viel Möglichkeiten, eine Datei als generiert zu markieren:
- Geben Sie in der EDITORCONFIG-Datei
generated_code = true
in einem Abschnitt an, der für diese Datei gilt. - Fügen Sie
<auto-generated>
oder<auto-generated/>
ganz oben in der Datei in einem Kommentar ein. Dabei kann es sich um eine beliebige Zeile des Kommentars handeln, jedoch muss es sich beim Kommentarblock um das erste Element in der Datei handeln. - Beginnen Sie den Dateinamen mit TemporaryGeneratedFile_ .
- Enden Sie den Dateinamen mit .designer.cs, .generated.cs, .g.cs oder .g.i.cs.
Generatoren können die Präprozessoranweisung #nullable
verwenden.
Standardmäßig sind die Nullable-Anmerkungs- und -Warnungskontexte deaktiviert. Dies bedeutet, dass Ihr vorhandener Code ohne Änderungen und ohne Warnungen kompiliert wird. Ab .NET 6 enthalten neue Projekte das <Nullable>enable</Nullable>
-Element in allen Projektvorlagen.
Diese Optionen bieten zwei unterschiedliche Strategien zum Aktualisieren einer vorhandenen Codebasis, um Nullable-Verweistypen zu verwenden.
Bekannte Fehlerquellen
Arrays und Strukturen, die Verweistypen enthalten, sind bekannte Fallstricke in Nullable-Verweisen und in der statischen Analyse, die die NULL-Sicherheit bestimmt. In beiden Fällen kann ein Non-Nullable-Verweis mit null
initialisiert werden, ohne Warnungen zu generieren.
Strukturen
Strukturen, die Verweistypen enthalten, die keine NULL-Werte zulassen, können Sie default
zuweisen, ohne dass Warnungen ausgelöst werden. Betrachten Sie das folgenden Beispiel:
using System;
#nullable enable
public struct Student
{
public string FirstName;
public string? MiddleName;
public string LastName;
}
public static class Program
{
public static void PrintStudent(Student student)
{
Console.WriteLine($"First name: {student.FirstName.ToUpper()}");
Console.WriteLine($"Middle name: {student.MiddleName?.ToUpper()}");
Console.WriteLine($"Last name: {student.LastName.ToUpper()}");
}
public static void Main() => PrintStudent(default);
}
Im Beispiel oben gibt es in PrintStudent(default)
keine Warnung, wenn die Non-Nullable-Verweistypen FirstName
und LastName
NULL sind.
Bei der Verwendung von generischen Strukturen tritt ein weiteres häufigeres Problem auf. Betrachten Sie das folgenden Beispiel:
#nullable enable
public struct Foo<T>
{
public T Bar { get; set; }
}
public static class Program
{
public static void Main()
{
string s = default(Foo<string>).Bar;
}
}
Im obigen Beispiel entspricht die Eigenschaft Bar
zur Laufzeit null
, und sie wird einer Non-Nullable-Zeichenfolge zugewiesen, ohne dass eine Warnung ausgelöst wird.
Arrays
Arrays stellen ebenfalls eine bekannte Fehlerquelle in Verweistypen dar, die NULL-Werte zulassen. Sehen Sie sich das folgende Beispiel an, das keine Warnungen auslöst:
using System;
#nullable enable
public static class Program
{
public static void Main()
{
string[] values = new string[10];
string s = values[0];
Console.WriteLine(s.ToUpper());
}
}
Im Beispiel oben zeigt die Deklaration des Arrays, dass dieses Non-Nullable-Zeichenfolgen enthält, während alle seine Elemente mit null
initialisiert werden. Anschließend wird der Variablen s
ein null
-Wert (das erste Element des Arrays) zugewiesen. Schließlich wird die Variable s
dereferenziert, was zu einer Laufzeitausnahme führt.
Siehe auch
.NET feedback
The .NET documentation is open source. Provide feedback here.
Feedback
Feedback senden und anzeigen für