[英]Generic abstract argument for method C#
我有這個代碼示例。 我不知道它為什么不編譯。 它不允許從D
轉換為A<B>
。
D
繼承A<C>
。 C
繼承B
,這意味着我應該能夠將D
傳遞給A<B>
方法參數吧? 我可能在這里遺漏了一些明顯的東西。
using System.Collections.Generic;
public class Program
{
public void Main()
{
var d = new D();
Foo(d); //Cannot convert D to A<B>
}
private void Foo(A<B> bar)
{
}
}
public abstract class A<TypeB> where TypeB : B
{
public abstract List<TypeB> list { get; set; }
}
public abstract class B
{
}
public class C : B
{
}
public class D : A<C>
{
public override List<C> list { get; set; }
}
這個問題已在本網站上被問過數百次。
假設你有一碗水果。 是一碗蘋果嗎? 蘋果是一種水果,為什么一碗水果不是一碗蘋果? 很明顯因為一碗水果已經含有香蕉,所以不是一碗蘋果。
假設你有一碗蘋果。 這是一碗水果嗎? 你想說“蘋果是一種水果,因此一碗蘋果就是一碗水果”。 但這是錯誤的。 一碗水果是你可以放入香蕉的東西 ,因為有一個操作,你可以在一碗水果上執行,你不能在一碗蘋果上執行,一碗蘋果不能用於碗的情況下水果預計。
您想要的轉換類型的技術名稱是“通用協變轉換”。 C#僅在少數特定情況下支持通用協變轉換:
IEnumerable<T>
。 您可以在期望IEnumerable<Fruit>
的上下文中使用IEnumerable<Apple>
,因為無法將香蕉放入IEnumerable<Fruit>
。 但是你不能將你的A<Apple>
類用作A<Fruit>
因為編譯器不相信你已經阻止了另一種類型Banana的可能性,它擴展了Fruit只用於接受Apple的方法。
在這個網站上搜索“協方差和逆變”,你會發現很多關於此的問題。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.