Visual Basic 2008 重大更改

更新: 2008 年 7 月

下表列出了可能阻止在 Visual Studio 2005 中创建的应用程序在 Visual Studio 2008 中进行编译,或可能更改该应用程序的运行时行为的所有更改。

类别

问题

说明

可以为 null 的类型

T 扩大为 T?在 Visual Studio 2008 中是预定义的转换。

在 Visual Studio 2005 中,可以创建用户定义的转换,以使 T 可以扩大为 Nullable(Of T)。为了更好地支持可以为 null 的类型,在 Visual Studio 2008 中预定义了此转换。

由于重载决策会同时考虑预定义转换和用户定义的转换,因此当两者同时存在时可能会出现多义性。因此,如果代码包含从 T 到 T? 的用户定义的扩大转换,该代码在 Visual Studio 2008 中可能是不明确的。

例如,在下面的代码中,对 c3.Sub1 的调用可在 Visual Studio 2005 中正常运行,但在 Visual Studio 2008 中会导致编译器错误。

若要解决此问题,可以移除用户定义的转换,也可以显式强制转换为 Class1 或 Class2:

重载决策

更正了泛型与非泛型类之间的重载决策差异。

Visual Studio 2005 中的一个 Bug 可能导致泛型类的重载决策行为与非泛型类的重载决策行为不同。在下面的示例中,Class1 和 Class2 基本相同,唯一区别是 Class2 上定义了一个泛型参数。Main 中对 c1.Sub1 的调用是不明确的,因为传入的参数可能会绑定到 Class1 中的 Sub1 的任一重载。这种多义性在 Visual Studio 2005 和 Visual Studio 2008 中都会导致编译器错误。

对 c2.Sub1 的调用应生成相同的错误,但在 Visual Studio 2005 中并非如此。该方法会绑定到 Class2 中的 Sub1 的不受约束的重载。

Visual Studio 2008 中修复了此问题。两种调用都会由于多义性而生成编译器错误。下面的代码说明了这一点:

若要解决此问题,可以更改重载以消除多义性,也可以显式指定类型参数:

重载决策

具有泛型和 ParamArray 参数的重载决策在 Visual Studio 2008 中会生成不同的结果。

重载决策的目标是尝试选择最合适的候选方法,该候选方法的形参应最为匹配传递给该方法的实参的类型。在本节的示例中,Sub1 在继承层次结构之中进行重载,并使用类型为 Integer 和 Short 的参数进行调用。

Visual Studio 2005 和 Visual Studio 2008 中的重载决策规则都指定直接匹配优于需要 ParamArray 参数的匹配。但是在使用 Visual Studio 2005 重载决策规则时,类型推理无法用于派生类 Class2 中的重载候选,因为 Y 不能同时为 Integer 和 Short,因而需要精确匹配。如果实参 sh 和 n 具有相同的类型,则 Class2 中的 Sub1 比 Class1 中的重载候选更为可取,因为后者有一个 ParamArray 形参。但是,由于这两个实参的类型不同,因此会改为选择 Class1 中的基类重载。T 会推断为 Integer,而 Short 扩大为 ParamArrayp。

Visual Studio 2008 使用一种新的算法,该算法选择的重载与 Visual Studio 2005 中选择的重载相同(除了在此特定情况下)。在 Visual Studio 2008 中,该算法在此示例中确定 Integer 为主导类型,因为 Short 扩大为 Integer。派生类中的类型参数 Y 推理为 Integer,而 Short 扩大为 Integer。因此,将调用派生类中的 Sub1。

通过在调用 Sub1 之前将变量 c2 强制转换为类型 C1ass1,或是通过将参数 sh 作为数组进行传递,可以强制执行 Visual Studio 2005 行为。

请参见

概念

重载决策

可以为 Null 的值类型

Visual Basic 中的泛型类型

参考

ParamArray

修订记录

日期

修订记录

原因

2008 年 7 月

新增主题。

信息补充。