gpt4 book ai didi

c# - 为什么不能在 C# 中动态调度基本访问表达式?

转载 作者:IT王子 更新时间:2023-10-29 04:24:42 25 4
gpt4 key购买 nike

我认为这个问题最好通过一个例子来理解,所以我们开始吧:

    public class Base {

// this method works fine
public void MethodA(dynamic input) {
// handle input
}

}

public class Derived: Base { // Derived was named Super in my original post

// This is also fine
public void MethodB(dynamic input) {
MethodA(input);
}

// This method does not compile and the compiler says:
// The call to method 'MethodA' needs to be dynamically dispatched,
// but cannot be because it is part of a base access expression.
// Consider casting the dynamic arguments or eliminating the base access.
public void MethodC(dynamic input) {
base.MethodA(input);
}

}

编译器明确指出方法 C 是无效的,因为它使用基访问来调用方法 A。但这是为什么呢?

重写一个带有动态参数的方法时,如何调用基方法?

例如如果我想做什么:

    public class Base {

// this method works fine
public virtual void MethodA(dynamic input) {
Console.WriteLine(input.say);
}

}

public class Derived: Base { // Derived was named Super in my original post

// this does not compile
public override void MethodA(dynamic input) {
//apply some filter on input
base.MethodA(input);
}

}

最佳答案

是的,这不是设计使然。 base.MethodA() 调用对虚拟方法进行非虚拟调用。在非动态情况下,编译器可以毫不费力地为此发出 IL,因为它知道需要调用什么特定方法。

动态调度不是这种情况。确定需要调用哪个特定方法是 DLR 的工作。它必须使用的是 Derived 类的 MethodTable。该表包含基类的 MethodA 方法的地址。它被覆盖覆盖。它所能做的就是调用 Derived.MethodA() 方法。这违反了基本关键字契约(Contract)。

关于c# - 为什么不能在 C# 中动态调度基本访问表达式?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3414265/

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