为什么可以';t词典<;T1,列表<;T2>>;被强制转换为Dictionary<;T1、IE

本文关键字:lt gt T1 IE Dictionary 转换 词典 列表 为什么 T2 | 更新日期: 2023-09-27 18:19:38

我想知道为什么我不能直接进行转换(我有一个模糊的想法,这可能与协变/逆变有关?),我是否被迫将第一个字典的元素复制到一个新字典中以获得我想要的类型?

为什么可以';t词典<;T1,列表<;T2>>;被强制转换为Dictionary<;T1、IE

不能这样做,因为它们不是同一类型。考虑:

        var x = new Dictionary<string, List<int>>();
        // won't compile, but assume it could...
        Dictionary<string, IEnumerable<int>> xPrime = x;
        // uh oh, would allow us to legally add array of int!
        xPrime["Hi"] = new int[13];

这有道理吗?因为Dictionary<string, List<int>>表示TValueList<int>,这意味着您可以将Add()作为值List<int>。如果可以将其强制转换为Dictionary<string, IEnumerable<int>>,则意味着值类型为IEnumerable<int>,这意味着可以Add()任何违反原始类型的IEnumerable<int>int[]HashSet<int>等)。

因此,List<T>可以转换为IEnumerable<T>引用,因为List<T>实现了IEnumerable<T>,但这并不意味着Dictionary<TKey, List<TValue>>实现/扩展了Dictionary<TKey, IEnumerable<TValue>>

更简单地说:

Dictionary<int, Dog> 

无法转换为

Dictionary<int, Animal>

因为后者允许您添加Cat、Squirrel等。

您不能强制转换,因为它仍然是Dictionary<T1, List<T2>>

比方说

Dictionary<string, List<int>> d1 = new Dictionary<string, List<int>>();
Dictionary<string, IEnumerable<int>> d2 = (Dictionary<string, IEnumerable<int>>)d1; // this is the invalid cast
d2["one"] = new int[0]; // valid for d2
List<int> list1 = d1["one"]; // would fail

是的,这是协方差的问题。我相信这是用.net 4.0 纠正的