键为列表的字典的行为方式
本文关键字:方式 字典 列表 | 更新日期: 2023-09-27 18:30:47
我正在使用遗留代码,我看到一个字典,其键是对象列表...
var myCrazyDictionary = new Dictionary<List<MyKeyObject>, List<MyValueObject>>();
这样的字典是如何表现的?您知道,由于引用类型...
它像这样神奇地工作吗?
// ????
myCrazyDictionary.Add(new List<MyKeyObject> { new MyKeyObject { Key1 = "1", Key2 = 2 } }, new List<MyValueObject> { new MyValueObject { Value = "!" } });
// ???????????
var result = myCrazyDictionary[new List<MyKeyObject> { new MyKeyObject { Key1 = "1", Key2 = 2 } }];
// Will this hold the value: "!" or crash or something else?
var byWhatBlackMagic = result[0].Value;
它就像你做了一个字典Dictionary<Object, List<MyValueObject>>
并且只是对添加和检索都做了一个new Object()
一样。 List<T>
不会覆盖Equals(object)
和GetHashCode()
,因此它只使用仅比较对象引用的默认行为。它不会查看列表内部进行比较。因此,当您尝试执行myCrazyDictionary[new List<MyKeyObject> { ... }]
时,您的示例将抛出KeyNotFoundException
,因为您正在创建一个"新对象"并且该新对象不在字典中(因为您刚刚创建了它)。
您可以获得所需的功能,只需创建自定义IEqualityComparer<List<MyKeyObject>>
并将其传递给字典的构造函数即可。
当心!如果您确实制作了自定义比较器,则在充当键的滚动时,List<MyKeyObject>
中与自定义Equals(List<MyKeyObject>, List<MyKeyObject>)
关联的任何内容或自定义.GetHashCode(List<MyKeyObject>)
都无法更改,否则您将破坏Dictionary
的内部逻辑。