繁体   English   中英

C#Late Binding和dynamic关键字不能一起使用

[英]C# Late Binding and dynamic keyword won't work together

我试图按照Pro C#5.0这本书中的例子,我偶然发现了一个我无法工作的例子:

static void Main() {

    Assembly asm = Assembly.Load("CarLibrary");

    Type MiniVan = asm.GetType("CarLibrary.MiniVan");

    dynamic d = Activator.CreateInstance(Minivan);

    Console.WriteLine("Type of d is {0}", d.GetType()); // Type is CarLibrary.MiniVan

    MethodInfo m = MiniVan.GetMethod("TurboBoost");
    m.Invoke(d, null); // This works fine, and prints out "Turbo Boosting"

    d.TurboBoost(); // This doesn't work like the book says it should. 
                    // I get: object does not contain a definition for TurboBoost;

这是CarLibrary的宣言:

namespace CarLibrary {

    // UPDATE: I just realized that I had declared MiniVan internal
    internal MiniVan {

        public void TurboBoost() {

            Console.WriteLine("Turbo Boosting");
        }
    }
}

因此,即使MiniVan被声明为INTERNAL,使用Reflection我仍然可以创建一个MiniVan实例,并调用TurboBoost()。 但是如果我使用dynamic关键字,则调用TurboBoost()不起作用。 如果MiniVan被声明为PUBLIC,两种情况都可以完美地运行。

有人可以告诉我,如果这是假设的那样吗?

dynamic尊重可访问性规则,其中不仅包括成员的可访问性,还包括对象的类型是internalprivate (嵌套的)等等。 dynamic 不仅仅是反射的包装 - 它更多: 这是否适用于常规C#从这里开始

这意味着CarLibrary程序集内执行相同的dynamic使用会起作用。 如果您想通过dynamic访问类型成员,那么它必须是public ,或者至少是:在调用上下文中可访问。

特别是,这可以防止您通过访问您从未应该直接了解internal类型的public成员来欺骗运行时。 例如,假设核心CLI类型实现了一些接口:

public ISomeInterface {...}
internal SomeMicrosoftType : ISomeInterface
{
    public void FireTheMissiles() {...}
}

现在; 可能有一个API将该对象公开ISomeInterface实例 - 因此我们可以合法地引用该对象。 在我们的常规代码中,我们可以访问ISomeInterface成员,但我们无法调用FireTheMissiles 但是,如果您的建议有效 ,那么我们可以这样做:

ISomeInterface innocent = ...
dynamic evil = innocent;
evil.FireTheMissiles();

现在, 是的,我们可以通过反射来做到这一点,但反射有额外的检查,特别是如果我们没有完全信任运行。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM