c# - 具有泛型类的泛型函数 : no implicit reference conversion

标签 c# generics implicit

我正在尝试通过引入通用函数来清理一些重复的代码块。但我没能做到这一点,而且我感觉我的类继承结构变得比我试图清理的代码更困惑......

以下是所涉及的类的抽象概述:

接口(interface):

interface Ia
interface Ib : Ia
interface Ic : Ib

类(class):

class Ca<T> where T : Ia
class Cb<T> : Ca<T> where T : Ia
class Cc : Cb<Ic>

功能:

void F<T>(T t) where T : Ca<Ib>

无效的函数调用:

F<Cc>(my_c);

错误:

The type 'Cc' cannot be used as type parameter 'T' in the generic type or method 'F<T>(T)'. There is no implicit reference conversion from 'Cc' to 'Ca<Ib>'.

我猜到错误中的“隐式”一词是指没有 where T : Ib 的事实在类定义中。所以我添加了另一个类

class Cb2<T> : Cb<T> where T : Ib

并制作Cc继承自Cb2而不是Cb 。但这导致了同样的错误。

谁能解释一下为什么会受到限制,以及我该如何解决它?

谢谢!

最佳答案

一般来说,C# 不允许泛型参数替换,即使它们是继承的类。当 variance 时,情况发生了变化添加了修饰符。

您需要的称为协方差,它允许使用派生类型代替泛型参数。但方差修饰符仅适用于接口(interface)和委托(delegate),因此 CaCbCc 应该是允许这样做的接口(interface)。你能得到的最接近的是:

interface Ia {}
interface Ib : Ia {}
interface Ic : Ib {}

interface Ca<out T> where T : Ia {}
interface Cb<out T> : Ca<T> where T : Ia {}
interface Cc : Cb<Ic> {}

class Main
{
    void F<T>(T t) where T : Ca<Ib>
    {}

    void M()
    {
      F<Cc>(null);
    }
}

注意 CaCb 定义中的 out T

More about out modifier

关于c# - 具有泛型类的泛型函数 : no implicit reference conversion,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31698283/

相关文章:

c# - .Net Core 2 OpenID Connect 身份验证和多重身份

c# - 从蓝牙接收字符串后使用线程更新标签

c# - 封闭式与开放式比较

java - 通过隐式向伴生对象添加方法

python - 需要解释 Python 中 json 和 dict 的区别

scala - Scala隐式对象与隐式val

c# - 从泛型类实现的接口(interface)调用泛型类中的泛型属性

c# - 如何绘制颜色范围较柔和的图像?

java - 为什么这个通用方法没有给出编译时错误?

typescript - 在Typescript中,如何获取在工厂(ish)函数中实例化的类上的方法的通用返回类型