我正在阅读Object.hashCode
hashCode
方法,它说
尽可能合理,Object类定义的hashCode方法确实为不同的对象返回不同的整数。 (这通常通过将对象的内部地址转换为整数[...]
来实现
但无论它的实现是什么,Integer.MAX+1
方法总是返回一个(让我们假设为正)整数,所以给定Integer.MAX+1
个不同的对象,其中两个将具有相同的哈希码。
为什么JavaDoc在这里“否认”冲突?这是一个实际的结论,因为使用了内部地址并且“来了,你永远不会在内存中同时拥有2015-12-17 11:37:38.0845 | 64 | INFO | -----------------------------------
2015-12-17 11:37:38.0845 | 64 | INFO | Statistics:
2015-12-17 11:37:38.0845 | 64 | INFO | Crawling Requests 46887 /min
2015-12-17 11:37:38.0845 | 64 | INFO | Stored Documents 9910 /min
2015-12-17 11:37:38.0845 | 64 | INFO | -----------------------------------
个对象,所以我们可以说它几乎总是唯一的” ?
这JavaDoc(谢谢bug entry)给出了我的意思(这似乎是一个超过10年的讨论):
似乎许多(可能是大多数)程序员认为这意味着默认实现,因此System.identityHashCode将产生唯一的哈希码。
资格“尽可能合理地实际”,实际上不足以说明哈希码在实践中并非不同。
答案 0 :(得分:3)
这些文档确实具有误导性,并且有一个bug在很久以前打开,说文档具有误导性,特别是实现是JVM
依赖的,并且在实践中特别是对于大量堆大小它在将对象标识映射到32位整数时,很可能会发生冲突
答案 1 :(得分:0)
这里有一个关于哈希码冲突的有趣讨论:
http://eclipsesource.com/blogs/2012/09/04/the-3-things-you-should-know-about-hashcode/
特别是,这突出了你的实际结论,“你永远不会在内存中同时拥有Integer.MAX + 1个对象,所以我们可以说它实际上总是独一无二的”距离准确很远birthday paradox
链接的结论是,假设hashCodes的随机分布,在我们有50/50的hashCode碰撞机会之前,我们只需要77,163个对象。
答案 2 :(得分:0)
当您仔细阅读本文时,您会注意到这只会意味着物品应该尽量避免碰撞(尽可能合理地实施'),但也不能保证您有不同之处不等对象的哈希码。
所以承诺不是很强,但它仍然非常有用。例如,在进行全面检查之前使用哈希码作为相等的快速指示。
例如ConcurrentHashMap将使用(在其上执行的函数)哈希码将位置分配给地图中的对象。在实践中,哈希码用于查找对象大致位于的位置,并且equals用于查找精确定位的对象。
如果对象不尽可能地尝试传播其哈希码,则哈希映射无法使用此优化。