使用动态和继承重载

时间:2013-11-18 21:32:01

标签: c# dynamic overloading dispatch

我遇到了一个问题,我需要动态调度(或者至少我认为应该调用它)具有继承结构。更具体地说,我想使用动态调度,以便在继承的类中添加更多特定的重载。我无法找到任何与我的问题完全相同的人(我发现在继承的课程中我总是谈论覆盖,我需要动态重载)。强烈简化的情况如下:

class A
{
    private void DoSpecificStuff(object a);
    private void DoSpecificStuff(SomeClass a);
}

class B<T> : A
{
    private void DoSpecificStuff(OtherClass<T> a);
}

然后在A 中,我有一些函数使用反射消耗某些类的字段。它是这样的:

public void Consume(JetAnotherClass a)
{
    // Fetch all fieldinfo's from a and for each fieldinfo, do this:
    foreach(FieldInfo info in a's fieldinfo's...)
            DoSpecificStuff((dynamic)fieldInfo.GetValue(a))
}

主叫网站的工作原理如下:

B b = new B();
b.Consume(new JetAnotherClass()); 

现在,每次 fieldInfo.GetValue(a)找到 SomeClass 的实例时,都会使用 SomeClass 调用所需的重载函数作为形式参数。但是当返回 OtherClass&lt;&gt; T&gt; 的实例时,会调用 DoSpecificStuff(对象a)而不是 DoSpecificStuff(OtherClass&lt;&gt; T&gt; ; a)

为什么我的动态调度在一个类中完美地工作,但是当另一个类提供应该动态调度的更多重载时会中断?动态调度是否通过查看最顶层实例(类型为 B ?)来开始?

PS:用(虚拟)保护或类似的东西取代私有无济于事。事实上,使用private确实可以解决 A 中的重载问题,因为我们使用隐式的 B 类型的参数调用DoSpecificStuff。

1 个答案:

答案 0 :(得分:1)

我认为你对单独的机制感到困惑:

  • 多态性 - 或运行时调用子类中的函数的能力,即使引用是基类类型。
  • 过载分辨率(通常没有dynamic)是最具体匹配函数的编译时分辨率。

当您使用dynamic将重载决策推迟到运行时时,您仍在进行重载解析。 Consume方法位于A,因此它只会查看A,并且不知道B甚至存在。

为了获得您想要的行为,我认为您应该创建一个单独的虚拟方法来调用包含DoSpecificStuff魔法的dynamic。然后在类B中重复该功能。这样,B的实例将使用B中的方法,并在执行重载解析时找到合适的候选者。