Tag: contravariance

使用通用接口约束时的协方差/逆差异难题

public interface IShape{} public class Rectangle : IShape{} public class Base{} public class Derived : Base{} public interface IFoo where T : IShape where U : Base { T Convert(U myType); } public class MyFoo : IFoo { public Rectangle Convert(Derived myType) { throw new NotImplementedException(); } } class Program { static void Main(string[] args) […]

逆变? 协方差? 这个通用架构有什么问题……?

我在设置命令处理架构时遇到了一些问题。 我希望能够创建从ICommand派生的许多不同的命令; 然后,创建从ICommandHandler派生的许多不同的命令处理程序; 这是我开始定义的接口和类: interface ICommand {} class CreateItemCommand : ICommand {} interface ICommandHandler where TCommand : ICommand { void Handle(TCommand command); } class CreateItemCommandHandler : ICommandHandler { public void Handle(CreateItemCommand command) { // Handle the command here } } 我有一个可以创建适当类型的命令的帮助程序类: class CommandResolver { ICommand GetCommand(Message message) { return new CreateItemCommand(); // Handle other commands […]

从Func 到Func 的转换工作但到Func 失败

我有以下代码: static Func s_objToString = (x) => x.ToString(); static Func s_stringToString = s_objToString; //compiles static Func s_intToString = s_objToString; //error 第二行编译,但第三行无法编译错误: 无法将类型’ System.Func ‘隐式转换为’ System.Func ‘ 这是为什么? 我理解,虽然字符串是从对象派生的,但是List并不是从List派生的,但是这里object是string工作而object是int失败,为什么呢? 好吧,让我说我理解为什么; 现在的问题是有一种解决方法(其他然后定义MyInt类到框int因为Func到Func工作)?

C#委托与lambda表达式的反演

下面的第二个测试方法不编译(不能将lambda表达式转换为目标类型D1 )。 这是否意味着(非generics)委托契约不适用于lambda表达式? [TestFixture] public class MyVarianceTests { private abstract class Animal {} private class Tiger : Animal {} private delegate Type D1(Tiger tiger); private static Type M1(Animal animal) { return animal.GetType(); } [Test] public void ContravariantDelegateWithMethod() { D1 func = M1; Type result = func(new Tiger()); Assert.AreEqual(result, typeof (Tiger)); } [Test] public void ContravariantDelegateWithLambda() […]

为什么C#(4.0)不允许generics类型中的共同和逆变?

这种限制的真正原因是什么? 这只是必须完成的工作吗? 概念上难吗? 这不可能吗? 当然,人们不能在字段中使用类型参数,因为它们总是可读写的。 但这不是答案,可以吗? 这个问题的原因是我在C#4上写了一篇关于方差支持的文章,我觉得我应该解释为什么它仅限于委托和接口。 只是为了逆转举证责任。 更新:埃里克问了一个例子。 怎么样(不知道这是否有意义,但是:-)) public class Lookup where T : Animal { public T Find(string name) { Animal a = _cache.FindAnimalByName(name); return a as T; } } var findReptiles = new Lookup(); Lookup findAnimals = findReptiles; 在一个类中拥有它的原因可能是类本身中保存的缓存。 请不要将您的不同类型的宠物命名为相同! 顺便说一下,这让我想到了C#5.0中的可选类型参数 🙂 更新2:我没有声称CLR和C#应该允许这个。 只是想了解是什么导致它没有。