这个问题来自关于元组的讨论.
我开始考虑元组应该具有的哈希码.如果我们接受KeyValuePair类作为元组怎么办?它不会覆盖GetHashCode()方法,所以可能它不会知道它的"子"的哈希码...所以,运行时将调用Object.GetHashCode(),它不知道真实的对象结构.
然后我们可以创建一些引用类型的实例,它们实际上是Equal,因为重载的GetHashCode()和Equals().并使用它们作为元组中的"孩子"来"欺骗"字典.
但它不起作用!运行时以某种方式计算出我们元组的结构并调用我们类的重载GetHashCode!
它是如何工作的?Object.GetHashCode()的分析是什么?
当我们使用一些复杂的密钥时,它会在某些不好的情况下影响性能吗?(可能,不可能的情况......但仍然)
以此代码为例:
namespace csharp_tricks { class Program { class MyClass { int keyValue; int someInfo; public MyClass(int key, int info) { keyValue = key; someInfo = info; } public override bool Equals(object obj) { MyClass other = obj as MyClass; if (other == null) return false; return keyValue.Equals(other.keyValue); } public override int GetHashCode() { return keyValue.GetHashCode(); } } static void Main(string[] args) { Dictionary
更新我想我已经在下面的答案中找到了解释.它的主要成果是:
小心你的密钥及其哈希码:-)
对于复杂的字典键,您必须正确覆盖Equals()和GetHashCode().
Pop Catalin.. 14
不要在可变类上覆盖GetHashcode()和Equals(),只在不可变类或结构上覆盖它,否则如果修改用作键的对象,哈希表将不再正常工作(你将无法在修改密钥对象后检索与密钥关联的值)
哈希表也不使用哈希码来识别他们使用密钥对象自己作为标识符的对象,并不要求用于在哈希表中添加条目的所有密钥都返回不同的哈希码,但是建议他们这样做,否则性能受苦很大
不要在可变类上覆盖GetHashcode()和Equals(),只在不可变类或结构上覆盖它,否则如果修改用作键的对象,哈希表将不再正常工作(你将无法在修改密钥对象后检索与密钥关联的值)
哈希表也不使用哈希码来识别他们使用密钥对象自己作为标识符的对象,并不要求用于在哈希表中添加条目的所有密钥都返回不同的哈希码,但是建议他们这样做,否则性能受苦很大