Col*_*lin 4 c# dynamic inner-classes
当我运行以下代码时,我得到了RuntimeBinderException: 'object' does not contain a definition for 'SetIt'.
public interface IInput { }
public interface IThing<in TInput>
{
void SetIt(TInput value);
}
public class ThingMaker
{
private class Thing<TInput> : IThing<TInput>
where TInput : IInput
{
public void SetIt(TInput value){}
}
private class Input : IInput {}
public IThing<IInput> GetThing()
{
return new Thing<IInput>();
}
public IInput GetInput()
{
return new Input();
}
}
class Program
{
static void Main(string[] args)
{
var thingMaker = new ThingMaker();
var input = thingMaker.GetInput();
dynamic thing= thingMaker.GetThing();
thing.SetIt(input);
}
}
Run Code Online (Sandbox Code Playgroud)
如果我切换thing到 avar它工作正常。如此明显,thing有SetIt。当我使用动态时,为什么会失败?任何有效的东西不应该var在它有效时也有效吗dynamic?
Thing<TInput>我认为这与成为私有内部类有关,因为当我将其公开时它会起作用。
这是您的问题的一个更简单的示例:
class A
{
class B
{
public void M() { }
}
public static object GetB() { return new B(); }
}
class Program
{
static void Main(string[] args)
{
dynamic o = A.GetB();
o.M();
}
}
Run Code Online (Sandbox Code Playgroud)
泛型和接口只是一种干扰。
问题是类型B(或者在您的情况下,Thing<IInput>)是私有类,因此在调用站点无法解析为实际类型。回想一下,这dynamic只是一个object变量,但编译已推迟到运行时。它的目的并不是让您在运行时做一些原本无法做的事情,并且“否则无法做”是根据调用站点的可访问类型来判断的(在本例中是这样的)情况下,是object)。
就运行时绑定器而言,类型很简单object(因此错误消息告诉您object不包含您想要的成员)。
当然,理论上可能可以dynamic以不同的方式实现,并且可以对有效类型进行更深入的搜索,它可以将对象视为将成员绑定到对象的目的(即实现的接口而不仅仅是对象的接口)。实际类型)。但这并不是它的实现方式,而且这样做的成本要高得多(无论是在原始设计和实现方面,当然还是在使用 的代码的运行时成本方面dynamic)。
相关阅读(可能重复):
| 归档时间: |
|
| 查看次数: |
185 次 |
| 最近记录: |