这是动态的错误吗?

问题描述

| 在泛型类上使用“ 0”实现动态调度时,并且泛型类型参数是另一个类上的私有内部类,运行时绑定程序将引发异常。 例如:
using System;

public abstract class Dispatcher<T> {
    public T Call(object foo) { return CallDispatch((dynamic)foo); }

    protected abstract T CallDispatch(int foo);
    protected abstract T CallDispatch(string foo);
}

public class Program {
    public static void Main() {
        TypeFinder d = new TypeFinder();

        Console.WriteLine(d.Call(0));
        Console.WriteLine(d.Call(\"\"));
    }

    private class TypeFinder : Dispatcher<CallType> {
        protected override CallType CallDispatch(int foo) {
            return CallType.Int;
        }

        protected override CallType CallDispatch(string foo) {
            return CallType.String;
        }
    }

    private enum CallType { Int,String }
}
在此,消息中将抛出“ 2”   \'Dispatcher.CallDispatch(int)\'由于其保护级别而无法访问 无法访问的原因是类型参数“ 3”是私有“ 4”,而“ 5”无法访问。因此,
CallDispatch
必须不可访问-但不是,因为because3 because可以访问。 这是
dynamic
的错误,还是不被支持?     

解决方法

        这是一个错误。如果您可以(并且可以)静态进行呼叫,则应该能够动态进行呼叫。 具体来说,以下代码有效:
using System;

public abstract class Dispatcher<T> {
    public T Call(object foo)
    {
        return CallDispatch(((object)(dynamic)foo).ToString());
    }

    protected abstract T CallDispatch(int foo);
    protected abstract T CallDispatch(string foo);
}

public class Program {
    public static void Main() {
        TypeFinder d = new TypeFinder();

        Console.WriteLine(d.Call(0));
        Console.WriteLine(d.Call(\"\"));
    }

    private class TypeFinder : Dispatcher<CallType> {
        protected override CallType CallDispatch(int foo) {
            return CallType.Int;
        }

        protected override CallType CallDispatch(string foo) {
            return CallType.String;
        }
    }

    private enum CallType { Int,String }
}
请注意,我已经使用ѭ10来使静态类型为人所知,C#编译器和CLR允许此上下文访问私有类型
CallType
,因此DLR也应允许它。     ,        这是一个错误,因为以下静态类型更改应等效
using System;

public abstract class Dispatcher<T>
{
    public T Call(int foo) { return CallDispatch(foo); }
    public T Call(string foo) { return CallDispatch(foo); }

    protected abstract T CallDispatch(int foo);
    protected abstract T CallDispatch(string foo);
}
而且有效。 这个问题似乎与编译器有关,它引起的dlr调用以及编译器在调用中包括的静态信息都是一个问题。可以与手动设置dlr调用的开源框架ImpromptuInterface一起使用。使用Impromptu,将上下文设置为
this
,可以从运行时类型(即TypeFinder)获取访问权限。
using System;
using ImpromptuInterface.Dynamic;
public abstract class Dispatcher<T>
{
    protected CacheableInvocation _cachedDynamicInvoke;

    protected Dispatcher()
    {
        _cachedDynamicInvoke= new CacheableInvocation(InvocationKind.InvokeMember,\"CallDispatch\",argCount: 1,context: this);
    }

    public T Call(object foo)
    {
        return (T) _cachedDynamicInvoke.Invoke(this,foo);
    }

    protected abstract T CallDispatch(int foo);
    protected abstract T CallDispatch(string foo);
}
    

相关问答

依赖报错 idea导入项目后依赖报错,解决方案:https://blog....
错误1:代码生成器依赖和mybatis依赖冲突 启动项目时报错如下...
错误1:gradle项目控制台输出为乱码 # 解决方案:https://bl...
错误还原:在查询的过程中,传入的workType为0时,该条件不起...
报错如下,gcc版本太低 ^ server.c:5346:31: 错误:‘struct...