2011-03-04 79 views
5

來自Bert Bates和Kathy Sierra國家的SCJP 6學習指南(其他要求)x.hashCode()!= y.hashCode()要求x .equals(y)== falseJava中的equals()和hashCode()合同

但是Javadoc for Object沒有明確提到這樣的要求。引用:
如果兩個對象根據equals(Object)方法相等,則對這兩個對象中的每一個調用hashCode方法必須產生相同的整數結果。

我應該採取什麼Javadoc說作爲一個重要的含義,如eq - > hc?那麼這兩個來源之間就不會有衝突。

回答

13

正如z5h所說,這些陳述是等同的。

對於邏輯條件x和y,「x implies y」與「!y implies!x」相同。

「如果是巴士,它是紅色的」在邏輯上等同於「如果某物不是紅色,那不是公交車。」

這是contraposition

我應該把Javadoc所說的物質含義如eq - > hc。

是的,這正是它說:兩個物體equals下等於暗示他們的散列碼必須相等。

+0

感謝您的澄清! – prasopes

+8

「如果是公共汽車,它是紅色的」你的英語水平如何:-) –

+0

喬恩,你可以給我任何例子,其中HashCode可以是相同的,但對象不相等? – UnKnown

12

這兩個語句是等價的。

簡而言之:

  1. 如果兩個哈希碼不同,對象是絕對不同的下等於。
  2. 如果兩個哈希碼相同,我們不知道。 (但在許多實際情況下,對象將是平等的)。
5

這些陳述之間沒有衝突,它們是等價的。

p: x.equals(y) 
q: x.hashCode() == y.hashCode() 
p implies q 
not q implies not p 
2

關於HashMap的基本情況。
1.無論對象類型如何,HashMap都會爲每個鍵生成哈希碼。
2.具體而言 - 哈希碼將基於鍵和值(即條目)

實驗產生: 考慮一個用戶定義的對象(例如SPObject)爲HashMap中的密鑰; SPObject只有一個參數(名稱)。請參閱:http://www.programcreek.com/2011/07/java-equals-and-hashcode-contract/

如果hashCode()和equals()在SPObject類中寫入不正確,則問題如下。
放入2個條目 - 新的SPObject(「SP」)&新的SPObject(「SP」)。這些被視爲不同的對象,併成功地存儲在地圖中。

map.get(new SPObject(「SP」))將返回null。
map.contains(new SPObject(「SP」))將返回false。

這是結果,如果hashCode /等於合同處理不當。

hashCode()  | equals() | Treated as | Description
No    |  No  | Duplicate | Stored in different buckets. 
              | Treated as different object. 

Yes   |  No  | Duplicate | Stored in same bucket. 
              | Treated as different object. 
              | Because, the default(Object) equals method will check only the reference of objects.  

No    |  Yes  | Duplicate | Stored in different buckets.Treated as different object 

Yes(hashlogic) |  Yes  | Unique  | Stored in same bucket.Treated as same object.Efficient. 

Yes(constant) |  Yes  | Unique  | Stored in same bucket.Treated as same object. 
              | Inefficient, because it will iterate bucket elements for equality check. 

+0

很好的解釋! – anandaravindan

0

背後hashCode的基本想法是,哪知道對象已經報告了什麼其他某些對象有權假定對象是不相等的不同的哈希碼值,而不必檢查他們的任何一個實體進一步。因爲整數支持與等價有關的各種公理,所以實體可能知道兩個哈希碼不同,而不直接比較它們。例如,知道其中一個報告了偶數,另一個是奇數就足以證明他們不匹配。這樣的假設通常允許實體快速識別大部分不可能包含正在查找的對象的集合,因此不會打擾檢查這些區域。

關於hashCode和equals的兩個引用「要求」都包括一個未說明的前提:在X.equals(Y)報告爲真的情況下,人們不希望實體錯誤地認爲它是假的。一般來說,代碼對錯誤假設採取行動是非常糟糕的,所以前提是人們不希望實體對對象平等做出不正確的假設是合理的。 「學習指南」引用這樣一個事實:如果兩個對象具有不相同的哈希碼,則它們將被推定爲不相等;使這種推定匹配現實需要他們不等。 JavaDoc基本上暗指這樣一個事實,即如果兩個對象是相等的,並且要避免讓實體假定它們不會並且沒有注意到它們,則必須確保由一個返回的值也將被返回另一個。

相關問題