C# 函数重载规则

发布于 2024-09-14 17:01:58 字数 532 浏览 1 评论 0原文

关于函数重载的规则是什么?

我有以下代码:

public T genericFunc<T>() where T : Component, new()
{
    T result = new T();
    overloadedFunction( result );
}

private overloadedFunction ( Component c ) // catch all function

private overloadedFunction ( DerivedFromComponent dfc) // specific function

当我使用以下代码调用上面的代码时:

genericFunc<DerivedFromComponent>();

我希望调用更具体的重载函数,但是调用了 catch all 函数,这是为什么?当单步执行上面的代码时,类型 T 确实是 DerivedFromComponent,我认为 CLR 在运行时选择了最好的匹配!

What are the rules regarding function Overloading?

I have the following code:

public T genericFunc<T>() where T : Component, new()
{
    T result = new T();
    overloadedFunction( result );
}

private overloadedFunction ( Component c ) // catch all function

private overloadedFunction ( DerivedFromComponent dfc) // specific function

when I call the above code with:

genericFunc<DerivedFromComponent>();

I expect the more specific overloadedFunction to be called, however the catch all function is called instead, why is this?. When stepping through the above code the type T is indeed DerivedFromComponent, I thought that the CLR picked the best possible match at runtime!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

当爱已成负担 2024-09-21 17:01:58

编译该方法时,编译器会在 genericFunc 中执行重载解析。编译该方法。此时它不知道您将提供什么类型参数,因此它只知道它可以调用您的第一个重载。

您使用泛型的示例使生活变得更加复杂,但重载总是在编译时解决(假设您没有使用动态)。

一个不使用泛型的简单示例:

void Foo(string text) { }
void Foo(object o) {}
...
object x = "this is a string";
Foo(x);

将调用第二个重载,因为 x编译时类型只是对象。

有关这方面的更多信息,请阅读我最近的有关重载的文章

The compiler performs overload resolution within genericFunc when that method is compiled. At that point it doesn't know what type argument you're going to provide, so it only knows that it can call the first of your overloads.

Your example using generics makes life more complicated, but overloads are always resolved at compile-time (assuming you're not using dynamic).

A simple example not using generics:

void Foo(string text) { }
void Foo(object o) {}
...
object x = "this is a string";
Foo(x);

would call the second overload, because the compile-time type of x is just object.

For more on this, read my recent article on overloading.

吃不饱 2024-09-21 17:01:58

Jon Skeet 的观点是正确的,重载解析是在编译时确定的。我想我应该添加另一个答案,这不是你问题的重点,但仍然值得注意。

在 C# 4 中,dynamic 关键字可用于将重载决策推迟到运行时。考虑以下打印的代码片段:

Base!
Derived!

class Base {
}

class Derived : Base {
}

void DoSomething(Base x) {
    Console.WriteLine("Base!");
}

void DoSomething(Derived x) {
    Console.WriteLine("Derived!");
}

void DoSomething<T>() where T: Base, new() {
    dynamic x = new T();
    DoSomething(x);
}

void Main()
{
    DoSomething<Base>();
    DoSomething<Derived>();
}

Jon Skeet is right on with regard to the fact that overload resolution is determined at compile time. I thought I'd add another answer that was not the point of your question but interesting to note nonetheless.

In C# 4, the dynamic keyword can be used to defer the overload resolution until runtime. Consider the following snippet which prints:

Base!
Derived!

class Base {
}

class Derived : Base {
}

void DoSomething(Base x) {
    Console.WriteLine("Base!");
}

void DoSomething(Derived x) {
    Console.WriteLine("Derived!");
}

void DoSomething<T>() where T: Base, new() {
    dynamic x = new T();
    DoSomething(x);
}

void Main()
{
    DoSomething<Base>();
    DoSomething<Derived>();
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文