java-「==」、equals和hashcode有什麼區別

1)"=="運算符是比較兩個變量的值是否相等。也就是說,該運算符用於比較變量對應的內存中所存儲的值是否相等,要比較兩個基礎類型的數據或兩個引用變量是否相等,只能使用"=="運算符。 編碼

    具體而言,若是兩個變量是基礎類型,能夠直接使用"=="運算符判斷對應的值是否相等。若是一個變量指向的是對象(引用類型),那麼,此時涉及兩塊內存,對象自己佔用一塊內存(堆內存),變量也佔用一塊內存,例如對於語句String s = new String(),變量s佔用一塊存儲空間,而new String()佔用另外一塊存儲空間,此時變量s所對應對應內存中的存儲數值就是對象佔用的那塊內存的首地址。對於指向類型的變量,若是判斷兩個變量是否指向一個相同的對象,即要比較這兩個變量對應的內存中的數值是否相同(這兩個變量是否指向同一個變量),這時能夠經過"=="運算符來進行比較,可是若是要比較這兩個對象的內容是否相等,使用"=="就沒法實現了。 spa

2)equals是Object對象中的方法,每一個Java類都繼承於Object,因此每個對象都具備equals方法,Object中的equals方法直接使用"=="運算符來比較兩個對象,因此在沒有覆蓋equals方法的狀況下,equals與"=="結果是同樣的,都是比較對象的引用。 code

    相比"=="運算符,equals方法的特殊之處就是能夠被覆蓋,因此能夠經過覆蓋,讓該方法比較的不是引用,而是咱們須要的數據內容,,例如,String類中的equals方法是用於比較兩個獨立的對象的內容是否相同,即堆中的內容是否相等,如下面的代碼爲例: 對象

String s1= new String("hello"); 繼承

String s2= new String("hello"); 內存

兩個new語句建立了兩個對象,而後分別用s1和s2指向一個對象,這是兩個不一樣的對象,他們的首地址是不相同的,即s1和s2存儲的數值是不相同的,因此表達式s1==s2將返回false,而這兩個對象的內容是相同的,因此equals方法將返回true。 md5

經過以上例子能夠說明,若是一個類沒有複寫euqals方法,那麼它就從Object中繼承equals方法,而且默認使用"=="運算符來進行比較,也就是在比較兩個對象的引用是否相同,所以equals和==會獲得相同的結果。若比較兩個獨立的對象,則總會返回false。若是編寫的類但願可以比較該類建立的兩個實例對象的內容是否相等,那麼必須覆蓋equals方法。 hash

3)hashCode()方法是從Object類中繼承的,它也鑑定兩個對象是否相等,Object類中的hashCode返回對象在內存中的地址的int值,因此在不重寫hashcode方法時,任何對象的hashcode都是不相同的。 基礎

    雖然equals也是比較兩個對象是否相等的,可是它和hashCode方法是有區別的。通常來說,equals方法是給用戶來使用的,若是要判斷兩個對象是否相等,須要覆蓋equals方法,而後在代碼中調用,這樣就能夠判斷它們是否相等了。對於hashCode方法用戶通常是不會調用它的,例如在hashMap中,因爲key是不重複的,它在判斷key是否重複的時候就調用了hashCode方法,並且也用類equals方法。此處不可重複,指的是,equals和hashCode方法中的一個不相同就能夠了。因此hashCode相等於一個對象的編碼表,就好像文件中的md5,它與equals方法的區別在於它的返回值是int類型,比較起來不直觀。 變量

    通常在覆蓋equals方法的同時也一樣須要覆蓋hashCode方法,不然,就會違反Object.hashCode的通用規則約定,從而致使沒法與全部基於散列表的集合類(hashMap hashSet hashTable)結合在一塊兒正常使用。

    hashCode方法和equals方法的關係以下:若是x.equals的返回值true,即兩個對象經過equals方法比較是相同的,那麼調用兩者的hashCode方法將返回相同的int值。若是x.equals的返回值false,即兩個對象經過quals方法比較的結果是不相同的,那麼x,y的hashCode的返回值可能相等也可能不相等。反之,hashCode的返回值不相等,必定能夠推出equals方法的返回值是不相等的,而hashCode的返回值相等,equals的返回值可能相等也可能不相等。

相關文章
相關標籤/搜索