Freigeben über


Wichtige Änderungen in Visual Basic 2008

Aktualisiert: Juli 2008

In der folgenden Tabelle sind alle Änderungen aufgeführt, die dazu führen können, dass eine in Visual Studio 2005 erstellte Anwendung in Visual Studio 2008 nicht kompiliert wird oder sich ihr Laufzeitverhalten ändert.

Kategorie

Problem

Beschreibung

Auf NULL festlegbare Typen

T, das zu T? erweitert wird, ist eine vordefinierte Konvertierung in Visual Studio 2008.

In Visual Studio 2005 können Sie eine benutzerdefinierte Konvertierung erstellen, sodass T zu Nullable(Of T) erweitert wird. Als Teil der verbesserten Unterstützung für auf NULL festlegbare Typen ist diese Konvertierung in Visual Studio 2008 vordefiniert.

Da bei der Überladungsauflösung sowohl vordefinierte als auch benutzerdefinierte Konvertierungen berücksichtigt werden, kommt es zu einer potenziellen Zweideutigkeit, wenn beides vorhanden ist. Daher ist Code, der eine benutzerdefinierte Erweiterungskonvertierung von T zu T? enthält, in Visual Studio 2008 möglicherweise doppeldeutig.

Im folgenden Code funktioniert der Aufruf von c3.Sub1 in Visual Studio 2005 beispielsweise, in Visual Studio 2008 wird jedoch ein Compilerfehler erzeugt.

Module Module1
Sub Main()
Dim c3 As New Class3
Dim sh As Short = 2
' The following statement compiles in Visual Studio 2005,
' but causes an error in Visual Studio 2008.
'c3.Sub1(sh)
End Sub
End Module
Class Class1
Public Shared Widening Operator CType(ByVal s As _
Nullable(Of Short)) As Class1
Return New Class1()
End Operator
End Class
Class Class2
Public Shared Widening Operator CType(ByVal n As Integer) As Class2
Return New Class2()
End Operator
End Class
Class Class3
Sub Sub1(ByVal c As Class1)
End Sub
Sub Sub1(ByVal c As Class2)
End Sub
End Class

Zur Lösung dieses Problems können Sie die benutzerdefinierte Konvertierung entfernen oder eine explizite Umwandlung nach Class1 oder Class2 durchführen:

c3.Sub1(CType(sh, Class1))

Überladungsauflösung

Unterschiede bei der Überladungsauflösung zwischen generischen und nicht generischen Klassen wurden korrigiert.

Ein Fehler in Visual Studio 2005 kann dazu führen, dass das Verhalten bei der Überladungsauflösung für generische Klassen gegenüber nicht generischen Klassen abweicht. Im folgenden Beispiel sind Class1 und Class2 identisch, mit der Ausnahme, dass in Class2 ein generischer Parameter definiert ist. Der Aufruf von c1.Sub1 in Main ist doppeldeutig, da das übergebene Argument an beide Überladungen von Sub1 in Class1 gebunden werden könnte. Die Doppeldeutigkeit verursacht sowohl in Visual Studio 2005 als auch in Visual Studio 2008 einen Compilerfehler.

Der Aufruf von c2.Sub1 sollte denselben Fehler generieren, in Visual Studio 2005 ist dies jedoch nicht der Fall. Stattdessen wird die Methode an die uneingeschränkte Überladung von Sub1 in Class2 gebunden.

Dieses Problem wird in Visual Studio 2008 behoben. Beide Aufrufe generieren wegen der Doppeldeutigkeit Compilerfehler. Dies wird durch folgenden Code veranschaulicht:

Module Module1
Sub Main()
Dim c1 As New Class1
Dim c2 As New Class2(Of String)
' The following statement causes a compiler error in both
' Visual Studio 2005 and Visual Studio 2008.
'c1.Sub1(New Nullable(Of Integer))
' The following statement causes a compiler error only
' in Visual Studio 2008.
'c2.Sub1(New Nullable(Of Integer))
End Sub
End Module
Class Class1
Sub Sub1(Of T)(ByVal arg As T)
Console.WriteLine("Unconstrained Sub1 in Class1")
End Sub
Sub Sub1(Of T As Structure)(ByVal arg As Nullable(Of T))
Console.WriteLine("Constrained Sub1 in Class1")
End Sub
End Class
Class Class2(Of U)
Sub Sub1(Of T)(ByVal arg As T)
Console.WriteLine("Unconstrained Sub1 in Class2")
End Sub
Sub Sub1(Of T As Structure)(ByVal arg As Nullable(Of T))
Console.WriteLine("Constrained Sub1 in Class2")
End Sub
End Class

Zur Lösung dieses Problems können Sie die Überladungen ändern, sodass sie nicht mehr doppeldeutig sind, oder Sie können die Typargumente explizit angeben:

c1.Sub1(Of Integer?)(New Nullable(Of Integer))
c2.Sub1(Of Integer?)(New Nullable(Of Integer))

Überladungsauflösung

Die Überladungsauflösung mit generischen Parametern und ParamArray-Parametern führt in Visual Studio 2008 zu verschiedenen Ergebnissen.

Ziel der Überladungsauflösung ist es, die infrage kommende Methode auszuwählen, deren Parameter am ehesten mit den Typen der Argumente übereinstimmen, die an die Methode übergeben werden. Im Beispiel in diesem Abschnitt wird Sub1 innerhalb einer Vererbungshierarchie überladen und mit Argumenten des Typs Integer und Short aufgerufen.

Die Regeln der Überladungsauflösung in Visual Studio 2005 und Visual Studio 2008 legen fest, dass direkte Übereinstimmungen bessere Übereinstimmungen sind als diejenigen, die ParamArray-Parameter erfordern. Mit den Regeln der Überladungsauflösung in Visual Studio 2005 schlägt der Typrückschluss für die Überladungsoption in der abgeleiteten Klasse Class2 jedoch fehl, da Y nicht Integer und gleichzeitig Short sein kann und exakte Übereinstimmungen erforderlich sind. Würden die Argumente sh und n denselben Typ aufweisen, würde Sub1 in Class2 gegenüber der Option in Class1 bevorzugt, die über einen ParamArray-Parameter verfügt. Da die beiden Argumente jedoch unterschiedliche Typen aufweisen, wird stattdessen die Basisklassenüberladung in Class1 ausgewählt. T wird als Integer abgeleitet, und Short wird zu ParamArrayp erweitert.

Visual Studio 2008 verwendet einen neuen Algorithmus, der dieselben Überladungen wie Visual Studio 2005 auswählt, mit Ausnahme dieses speziellen Falls. In Visual Studio 2008 bestimmt der Algorithmus, dass Integer der dominante Typ in diesem Beispiel ist, da Short zu Integer erweitert wird. Der Typparameter Y in der abgeleiteten Klasse wird als Integer abgeleitet, und Short wird zu Integer erweitert. Dadurch wird Sub1 in der abgeleiteten Klasse aufgerufen.

Module Module1
Sub Main()
Dim c2 As New Class2
Dim n As Integer
Dim sh As Short
c2.Sub1(n, sh)
End Sub
Class Class1
Sub Sub1(Of T)(ByVal arg1 As T, ByVal ParamArray p() As Integer)
Console.WriteLine("Visual Studio 2005 calls Sub1 " & _
"in the *base* class.")
End Sub
End Class
Class Class2 : Inherits Class1
Overloads Sub Sub1(Of Y)(ByVal arg1 As Y, ByVal arg2 As Y)
Console.WriteLine("Visual Studio 2008 calls Sub1 " & _
"in the *derived* class.")
End Sub
End Class
End Module

Sie können das Verhalten von Visual Studio 2005 erzwingen, indem Sie die Variable c2 in den Typ C1ass1 umwandeln, bevor Sub1 aufgerufen wird, oder indem das Argument sh als Array übergeben wird.

' You can cast variable c2 to Class1 in order to force Visual
' Studio 2005 behavior.
CType(c2, Class1).Sub1(n, sh)
' Alternatively, you can pass sh as an array.
c2.Sub1(n, New Integer() {sh})

Siehe auch

Konzepte

Überladungsauflösung

Auf NULL festlegbare Werttypen

Generische Typen in Visual Basic

Referenz

ParamArray

Änderungsprotokoll

Date

Versionsgeschichte

Grund

Juli 2008

Thema hinzugefügt.

Informationsergänzung.