爲何重寫 equals() 方法,必定要重寫 hashCode() 呢?| HashMap

微信搜索🔍「碼農田小齊」,關注這個在紐約的程序媛,回覆「01-05」能夠獲取計算機精選書籍、我的刷題筆記、大廠面經、面試資料等資源,麼麼噠~git

首先咱們有一個假設:任何兩個 object 的 hashCode 都是不一樣的。github

那麼在這個條件下,有兩個 object 是相等的,那若是不重寫 hashCode(),算出來的哈希值都不同,就會去到不一樣的 buckets 了,就迷失在茫茫人海中了,再也沒法相認,就和 equals() 條件矛盾了,證畢。web

撒花~~🎉🎉🎉面試

接下來咱們再對這兩個方法一探究竟:數組

其實 hashCode() 和 equals() 方法都是在 Object class 這個老祖宗裏定義的,Object 是全部 Java 中的 class 的鼻祖,默認都是有的,甩不掉的。微信

那既然是白給的,咱們先來看看大禮包裏有什麼,谷歌 Object 的 Oracle 文檔:編輯器

因此這些方法都是能夠直接拿來用的呢~ide

回到 hashCode() 和 equals(),那麼若是這個新的 class 裏沒有重寫 (override) 這兩個方法,就是默認繼承 Object class 裏的定義了。學習

那咱們點進去來看看 equals() 是怎麼定義的:flex

記筆記:

equals() 方法就是比較這兩個 references 是否指向了同一個 object.

嗯???你在逗我嗎??那豈不是和 == 同樣了??

補充:
咱們經常使用的比較大小的符號之 ==
若是是 primitive type,那麼 == 就是比較數值的大小;
若是是 reference type,那麼就比較的是這兩個 reference 是否指向了同一個 object。

再補充:
Java 的數據類型能夠分爲兩種:
Primitive type 有且僅有8種:byte, short, int, long, float, double, char, boolean.
其餘都是 Reference type.
因此雖然 Java 聲稱 「Everything is object」,可是仍是有非 object 數據類型的存在的。

我不信,我要去源碼裏看看它是怎麼實現的。

哈,還真是的,繞了這麼半天,equals() 就是用 == 來實現的!

那爲何還弄出來這麼個方法呢?

答:爲了讓你 override~

好比通常來講咱們比較字符串就是想比較這兩個字符串的內容的,那麼:

str1 = 「tianxiaoqi」;
str2 =  new String(「tianxiaoqi」);

str1 == str2; // return false
str1.equals(str2); // return true 

由於 String 裏是重寫了 equals() 方法的:

老祖宗留給你就是讓你本身用的,若是你不用,那人家也提供了默認的方法,也是夠意思了。

好了,咱們再去看 hashCode() 的介紹:

那至於 hashCode() 返回的到底是什麼,和本文關聯不太大,有興趣的同窗能夠看參考這篇文章[1],結論就是:

返回的並不必定是對象的(虛擬)內存地址,具體取決於運行時庫和JVM的具體實現。

但不管是怎麼實現的,都須要遵循文檔上的約定,也就是對不一樣的 object 會返回惟一的哈希值

因此說,

hashCode() 決定了 key 放在這個桶裏的編號,也就是在數組裏的 index;

equals() 是用來比較兩個 object 是否相同的。

若是你喜歡這篇文章,記得給我點贊留言哦~大家的支持和承認,就是我創做的最大動力,咱們下篇文章見!

我是小齊,紐約程序媛,終生學習者,天天晚上 9 點,雲自習室裏不見不散!

更多幹貨文章見個人 Github: https://github.com/xiaoqi6666/NYCSDE

參考資料

[1]

hashCode()參考文章: https://blog.csdn.net/xusiwei1236/article/details/45152201

相關文章
相關標籤/搜索