gpt4 book ai didi

c# - 为什么类型约束不是方法签名的一部分?

转载 作者:太空狗 更新时间:2023-10-29 17:55:23 24 4
gpt4 key购买 nike

更新:从 C# 7.3 开始,这应该不再是一个问题。来自发行说明:

When a method group contains some generic methods whose type arguments do not satisfy their constraints, these members are removed from the candidate set.

C# 7.3 之前的版本:

所以我读了Eric Lippert's 'Constraints are not part of the signature' ,现在我明白规范指定在重载解析之后检查类型约束,但我仍然不清楚为什么必须这样。下面是埃里克的例子:

static void Foo<T>(T t) where T : Reptile { }
static void Foo(Animal animal) { }
static void Main()
{
Foo(new Giraffe());
}

这不会编译,因为重载决议:Foo(new Giraffe())推断 Foo<Giraffe>是最好的重载匹配,但随后类型约束失败并抛出编译时错误。用埃里克的话来说:

The principle here is overload resolution (and method type inference) find the best possible match between a list of arguments and each candidate method’s list of formal parameters. That is, they look at the signature of the candidate method.

类型约束不是签名的一部分,但为什么不能呢?在哪些情况下,将类型约束视为签名的一部分是个坏主意?是难以实现还是无法实现?我并不是在提倡如果最佳选择的过载由于某种原因无法调用,那么就默默地退回到第二好的;我会讨厌那个。我只是想了解为什么不能使用类型约束来影响最佳重载的选择。

我想象在 C# 编译器内部,仅出于重载解析目的(它不会永久重写方法),如下所示:

static void Foo<T>(T t) where T : Reptile { }

转换为:

static void Foo(Reptile  t) { }

为什么不能将类型约束“引入”形式参数列表?这如何以任何不好的方式改变签名?我觉得它只会加强签名。然后 Foo<Reptile>永远不会被视为过载候选对象。

编辑 2:难怪我的问题如此令人困惑。我没有正确阅读 Eric 的博客,我引用了错误的例子。我在我认为更合适的示例中进行了编辑。我还将标题更改为更具体。这个问题似乎不像我最初想象的那么简单,也许我遗漏了一些重要的概念。我不太确定这是 stackoverflow 的 Material ,最好将这个问题/讨论转移到其他地方。

最佳答案

C# 编译器不必将类型约束视为方法签名的一部分,因为它们不是 CLR 方法签名的一部分。如果重载决议对不同语言的工作方式不同,那将是灾难性的(主要是由于动态绑定(bind)可能在运行时发生并且不应该因一种语言而异于另一种语言,否则一切都会崩溃)。

为什么决定这些约束不成为 CLR 方法签名的一部分是另一个问题,对此我只能做出不明智的假设。我会让知情人士回答这个问题。

关于c# - 为什么类型约束不是方法签名的一部分?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9440888/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com