问题标签 [covariance]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
generics - 在 .NET 4 中使用带有接口基类型的协方差?
我有一些使用 LINQ-to-SQL 创建的实体。其中六个实体(主要在下拉列表中表示值)实现了我称为IValue
. 我这样做是因为 UI 层将不得不考虑几个特殊情况——特别是,如果记录上的原始值已被标记为已删除,将显示什么。
ListAllXXX
存储库为这些人提供了多种方法。所有这些都返回类型为适当实体类型的通用列表。一个例子:
ContactType
确实实现IValue
了,当然。
还有另一组服务旨在实际检索特定于 UI 的列表。因此,基本模式是:
(我可能应该注意到这DummyValue
是我创建的一个简单的类,它也实现了IValue
,它的全部目的是充当“添加新”和“删除”菜单选项。)
所有这一切都是因为我不想编写几十行几乎相同的代码——这就是我认为我们有协方差的全部原因。
此处编写的代码无法编译。我试过手动投到List<IValue>
就ListAllContactTypes
行了;编译,但在运行时失败并出现无效的强制转换异常。
我怎样才能到达我想去的地方?对接口使用泛型变量是否有限制?如果是这样,有没有简单的方法解决它?如果不是,我是否会沦为编写一堆高度重复但略有不同的代码?(我真的很想避免。)
这很可能是重复的,但我的 Google-fu 现在让我失望了。如果是,请相应地投票关闭。(如果是这样的话,我会投票赞成!)
c# - 关于 C# 4.0 的泛型协方差的问题
定义了这个接口:
为什么以下代码有效:
这不是吗?:
它与 int 作为值类型有什么关系吗?如果是,我该如何规避这种情况?
谢谢
c# - C# 4.0 中的协方差和逆变推理
当我们在 C# 4.0 中定义接口时,我们可以将每个泛型参数标记为in
或out
。如果我们尝试将泛型参数设置为 out 并且会导致问题,编译器会引发错误,不允许我们这样做。
问题:
如果编译器有办法推断covariance
( out
) 和contravariance
( in
) 的有效用途,为什么我们必须这样标记接口?让我们像往常一样定义接口,当我们尝试在客户端代码中使用它们时,如果我们尝试以不安全的方式使用它们会引发错误,这还不够吗?
例子:
还,
这不是Java在相同情况下所做的吗?据我记得,你只是做类似的事情
还是我在混合东西?
谢谢
.net - .NET 4.0 通用不变量、协变、逆变
这是我面临的情况:
现在,当我尝试将 UserDataAccessLayer 转换为它的通用基类型ITableDataAccessLayer<TableRecord>
时,编译器抱怨它不能隐式转换类型。
当我尝试在泛型参数的接口声明中使用in
orout
关键字时,编译器会抱怨Invalid variance: The type parameter must be invariantly valid。
我有以下抽象类:
示例具体实现如下:
返回新的用户数据访问层();是编译器抱怨的地方。
c# - 这是 C# 4 中的协方差错误吗?
在下面的代码中,我希望能够从elements
to隐式转换,baseElements
因为TBase
它可以隐式转换为IBase
.
但是,我收到评论中提到的错误。
引用规范:
如果是使用变体类型参数声明的接口或委托类型,并且对于每个变体类型参数,则类型可以变型
T<A1, …, An>
转换为类型,并且以下内容之一成立:T<B1, …, Bn>
T
T<X1, …, Xn>
Xi
Xi
是协变的,并且存在从Ai
到的隐式引用或身份转换Bi
Xi
是逆变的,并且存在从Bi
到的隐式引用或身份转换Ai
Xi
是不变的,并且存在从Ai
到的身份转换Bi
检查我的代码,它似乎与规范一致:
IEnumerable<out T>
是一个接口类型IEnumerable<out T>
用变体类型参数声明T
是协变的TBase
从到存在隐式引用转换IBase
那么 - 这是 C# 4 编译器中的错误吗?
c# - 在这种假设情况下,是否有可能在 C# < 4 中围绕泛型协方差进行最终运行?
假设我有一个小的动物继承层次结构:
接下来,这是一个界面,提供了一种转换strings
为IAnimals
.
最后,这是这样做的一种策略:
现在,问题。是否可以替换标记为 [1]、[2] 和 [3] 的部分,以便该程序能够正确编译和运行?如果不接触 [1]、[2] 和 [3] 以外的部分就无法做到这一点,您是否仍然可以从包含 IAnimal 任意实现的集合中IAnimal
的每个实例中获取一个?Transmogrifier
你能从一开始就形成这样一个集合吗?
vb.net - 是否可以在 VB.NET 中覆盖属性并返回派生类型?
考虑以下代表排序系统的类:
现在,假设我们想将这些类扩展为一组更具体的订单类,同时保持 OrderBase 的聚合性质:
WebOrder 类中的 Overriden 属性将导致错误,指出返回类型与 OrderBase 中定义的不同……但是,返回类型是 OrderBase 中定义的类型的子类。为什么VB不允许这样做?
c#-4.0 - 我可以有一个既是协变又是逆变的类型,即与子类型和超类型完全可替代/可更改的类型?
我可以有一个可以协变和逆变的类型(现在忘记它的语义)吗?
例如:
转至 Eric Lippert 的博客,了解 C# 4.0 中的差异,因为几乎没有其他任何地方涵盖了该主题的充分基础。
无论如何我都试过了,它不仅不允许这样做,而且告诉我我错过了整点。我需要了解只读、只写和方差之间的联系。
我想我还有一些阅读要做。
但与此同时,任何简短的、顿悟的答案都是受欢迎的。
c# - C# 编译器无法识别一个类正在实现一个接口
以下代码无法编译(使用 VS2010),我不明白为什么。编译器应该能够推断出与List<TestClass>
'兼容'(抱歉没有更好的词)IEnumerable<ITest>
,但不知何故它不。我在这里想念什么?
编译器给出两个错误:
'ConsoleApplication1.Program.Test(System.Collections.Generic.IEnumerable<ConsoleApplication2.ITest>)' 的最佳重载方法匹配有一些无效参数
参数 1:无法从 'System.Collections.Generic.List<ConsoleApplication2.TestClass>' 转换为 'System.Collections.Generic.IEnumerable<ConsoleApplication2.ITest>'
.net - 检测接口泛型类型参数的差异
有没有办法反映接口以检测其泛型类型参数和返回类型的差异?换句话说,我可以使用反射来区分这两个接口:
两者的 IL 看起来相同。