具有通用约束的通用接口无法强制转换

时间:2019-05-15 13:59:00

标签: c# generics interface casting covariance

我有一个通用接口,该接口具有接口约束,这是由于 我无法像我想要的那样协变。并且必须依靠动态。理想情况下,我想摆脱这一点,但找不到解决办法。

我们可以认为此问题类似于WebApi控制器。 我将有一个字符串和有效载荷一起输入。根据字符串名称,我需要选择适当的“策略”(控制器/方法)来运行并传递有效负载。

我也希望它能够自动工作,这意味着:我有一些“反射”代码,用于查找所有使用IAnimalAction <>的类,将它们加载到集合中,并设置DI容器。所有这些都能正常工作。

正如您在代码中看到的那样,动态效果完美,但是我想避免运行时异常,并在构建时将其包含。

 public interface IAnimalType
    { }

    public class Cat : IAnimalType
    { public string Name;} 
    public class Dog : IAnimalType
    { public int EvilFactor;} 
    public class Cow : IAnimalType
    { }

    public interface IAnimalAction<T> where T : IAnimalType
    {
        bool ActUpon(T input);
    }
    public class IgnoreAnimal: IAnimalAction<Cat>
    {
        public bool ActUpon(Cat input)
        {
            return true;
        }
    }
    public class LoveAnimal: IAnimalAction<Dog>, IAnimalAction<Cow>
    {
        public bool ActUpon(Dog input)
        {
            return true;
        }

        public bool ActUpon(Cow input)
        {
            return true;
        }
    }

    public class test
    {
        public test()
        {
            var cat = new Cat();
            var ignoreAction= SomeStaticInstance.GetRelevantAction(cat. GetType().Name);// returns new IgnoreAnimal(); in this case
            var works = ((IAnimalAction<Cat>)ignoreAction).ActUpon(cat);
            var alsoWorks= ((dynamic)ignoreAction).ActUpon(cat);
            var doesnt= ((IAnimalAction<IAnimalType>)ignoreAction).ActUpon(constraint);


        }
    }

我希望能够确保方法'ActUpon'在我的实例上始终可用。

我了解协方差和逆方差的问题,但我认为必须有其他不依赖动态的方法。

由于我通过反射加载了我的类,并且仅加载了实现“接口IAnimalAction”的类,因此我认为它可以安全地保留,可以选择在接口中查找方法名称并让代码调用已解析的方法名,而不是硬编码“ ActUpon”。

将示例更新为少一些抽象

0 个答案:

没有答案