更新: 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
修订记录