Heim >Backend-Entwicklung >C++ >Welche unerwarteten Verhaltensweisen und Eckfälle gibt es in C# und .NET?
C# und .NET: Enthüllung versteckter Überraschungen
Softwareentwicklung offenbart oft unerwartete Verhaltensweisen. C# und .NET sind zwar leistungsstark, bilden aber keine Ausnahme. In diesem Artikel werden einige interessante Eckfälle untersucht, die selbst erfahrene Entwickler vor Herausforderungen stellen können.
String-Erstellung: Ein kontraintuitives Ergebnis
Betrachten Sie diesen scheinbar einfachen Codeausschnitt:
<code class="language-csharp">string x = new string(new char[0]); string y = new string(new char[0]); Console.WriteLine(object.ReferenceEquals(x, y));</code>
Die Ausgabe ist True
und widerspricht der Erwartung, dass new
unterschiedliche Objekte für Referenztypen erstellt. Die Common Language Runtime (CLR) optimiert dieses spezielle Szenario, indem sie dieselbe leere Zeichenfolgeninstanz wiederverwendet.
Generische Typen und Nullable
Der folgende Code zeigt ein weiteres unerwartetes Verhalten:
<code class="language-csharp">static void Foo<T>() where T : new() { T t = new T(); Console.WriteLine(t.ToString()); // Works fine Console.WriteLine(t.GetHashCode()); // Works fine Console.WriteLine(t.Equals(t)); // Works fine // This throws a NullReferenceException... Console.WriteLine(t.GetType()); }</code>
Wenn T
Nullable<T>
ist (z. B. int?
), tritt beim Aufruf von NullReferenceException
ein GetType()
auf. Dies liegt daran, dass Nullable<T>
die meisten Methoden überschreibt, nicht jedoch GetType()
. Der Boxing-Prozess während des Aufrufs des nicht überschriebenen GetType()
führt zu einem Nullwert.
Proxy-Attribute und die new()
Einschränkung: Erwartungen trotzen
Ayende Rahien hat ein ähnliches, aber komplexeres Szenario hervorgehoben:
<code class="language-csharp">private static void Main() { CanThisHappen<MyFunnyType>(); } public static void CanThisHappen<T>() where T : class, new() { var instance = new T(); // new() on a ref-type; should be non-null, then Debug.Assert(instance != null, "How did we break the CLR?"); }</code>
Überraschenderweise kann dieser Code die Behauptung nicht erfüllen. Durch die Verwendung eines Proxy-Attributs (wie MyFunnyProxyAttribute
), das den new()
-Aufruf abfängt und null
zurückgibt, kann die Behauptung verletzt werden. Dies zeigt das Potenzial für unerwartete Wechselwirkungen zwischen Laufzeitverhalten und benutzerdefinierten Attributen. Diese Beispiele verdeutlichen, wie wichtig gründliche Tests und ein tiefes Verständnis des Innenlebens der CLR sind, um unerwartete Fallstricke bei der C#- und .NET-Entwicklung zu vermeiden.
Das obige ist der detaillierte Inhalt vonWelche unerwarteten Verhaltensweisen und Eckfälle gibt es in C# und .NET?. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!