具有多个泛型的方差 parameters/constraints
Variance with multiple generic parameters/constraints
首先,我什至不知道这个问题是否正确,因为我不确定问题到底是什么。以这些接口作为初学者:
public interface IItemContainer<TValue, TItem> where TItem : IItem<TValue>
{
List<TItem> Items { get; set; }
}
public interface IItem<T>
{
T Value { get; set; }
}
我是这样实现的:
public class ItemContainer1<TValue> : IItemContainer<TValue, Item1<TValue>>
{
public List<Item1<TValue>> Items { get; set; }
}
public class Item1<T> : IItem<T>
{
public T Value { get; set; }
}
到目前为止一切正常,但我在以下作业中遇到 "Cannot implicitly convert" 转换错误:
IItemContainer<string, IItem<string>> container = new ItemContainer1<string>();
如果我尝试像这样投射,我会得到 InvalidCastException
:
IItemContainer<string, IItem<string>> container =
(IItemContainer<string, IItem<string>>)new ItemContainer1<string>();
有些事情告诉我,我的通用参数或约束有误(或两者都有)。这可能是一个方差问题,我还没有完全解决这个问题。我需要做什么才能完成这项工作?
编辑:我不是 TItem
参数的超级粉丝,但这是我知道的使 List<TItem>
属性 成为 [=18= 类型的唯一方法] 而不是 List<IItem<TValue>>
.
因为您希望列表的类型为 Item1<TValue>
,所以您不能将其转换为不太具体的 IItem<TValue>
。 IItem<TValue>
类型的 属性 上的 setter 应该对接口的任何有效实现者成功。您要么需要允许您声明不想要的 IItem<TValue>
类型的列表,要么以另一种方式重新构建。
如果您只需要将列表值读取为 IItem<TValue>
,而不是使用界面创建新列表,您可以更改界面以读取和转换值。
首先,我什至不知道这个问题是否正确,因为我不确定问题到底是什么。以这些接口作为初学者:
public interface IItemContainer<TValue, TItem> where TItem : IItem<TValue>
{
List<TItem> Items { get; set; }
}
public interface IItem<T>
{
T Value { get; set; }
}
我是这样实现的:
public class ItemContainer1<TValue> : IItemContainer<TValue, Item1<TValue>>
{
public List<Item1<TValue>> Items { get; set; }
}
public class Item1<T> : IItem<T>
{
public T Value { get; set; }
}
到目前为止一切正常,但我在以下作业中遇到 "Cannot implicitly convert" 转换错误:
IItemContainer<string, IItem<string>> container = new ItemContainer1<string>();
如果我尝试像这样投射,我会得到 InvalidCastException
:
IItemContainer<string, IItem<string>> container =
(IItemContainer<string, IItem<string>>)new ItemContainer1<string>();
有些事情告诉我,我的通用参数或约束有误(或两者都有)。这可能是一个方差问题,我还没有完全解决这个问题。我需要做什么才能完成这项工作?
编辑:我不是 TItem
参数的超级粉丝,但这是我知道的使 List<TItem>
属性 成为 [=18= 类型的唯一方法] 而不是 List<IItem<TValue>>
.
因为您希望列表的类型为 Item1<TValue>
,所以您不能将其转换为不太具体的 IItem<TValue>
。 IItem<TValue>
类型的 属性 上的 setter 应该对接口的任何有效实现者成功。您要么需要允许您声明不想要的 IItem<TValue>
类型的列表,要么以另一种方式重新构建。
如果您只需要将列表值读取为 IItem<TValue>
,而不是使用界面创建新列表,您可以更改界面以读取和转换值。