Java中的equals、hashCode、==

本著針對面試,不負責任的態度,寫下《面試總結》系列。本系列記錄面試過程中各個知識點,而不是入門系列,如果有不懂的自行學習。

暢所欲言,歡迎來噴。


轉載請標明出處,本文地址:http://www.lxweimin.com/p/b7f28817bad1

不負責任系列


面試中經常會問到這類問題。如下:

String s1="123";
String s2="123";
String s3=new String("123");
System.out.println(s1==s2);
System.out.println(s1==s3);
System.out.println(s1.equals(s2));
  1. 兩個類對象的hashCode相等,對象相等嗎?equals相等,對象相等嗎?

以上兩種算是一類問題。

首先,要說1中==操作的問題,對String賦值,而非new出來的對象,這類值通常會存放在常量池中,不會在堆中創建對象,所以s1與s2指向的是同一個地址。s3是new出來的,那么會在堆中創建對象,在s3指向的是堆中的地址,所以s1==s3比較的是地址。

其次,equals操作,由于String類中重寫了equals方法,而Object類中的equals方法是直接做的==比較。

//Object.java
public boolean equals(Object obj) {
        return (this == obj);
    }

String類中重寫了equals()方法

//String.java
public boolean equals(Object anObject) {
       if (this == anObject) {
            return true;
        }
        if (anObject instanceof String) {
            String anotherString = (String)anObject;
            int n = value.length;
            if (n == anotherString.value.length) {
                char v1[] = value;
                char v2[] = anotherString.value;
                int i = 0;
                while (n-- != 0) {
                    if (v1[i] != v2[i])
                        return false;
                    i++;
                }
                return true;
            }
        }
        return false;

從源碼中可以看到,先從==判斷,這個判斷的是引用,如果不想等,接下來是循環字符串,判斷的字符串里面的內容,如果每個字符都相等,兩個String對象才相等。

從String類引申出來,我們能不能直接說==判斷的是對象的地址,equals()判斷的是對象的內容呢?
答案是不可以,那么為什么呢?
==判斷的是兩個對象的地址,這個毋庸置疑,但是equals()這個是不確定的。

我們知道equals()方法是Object中的,也就是說,所有的對象都可以去覆蓋重寫該方法。沒有重寫equals()的時候,默認的equals()方法,等價于==方法。如果像String中那樣,每個類都有自己的邏輯,自定義個類,重寫equals()方法,恒返回true,那么怎么能夠判斷出來對象是相等呢?或者如學生類,重寫equals()的時候,判斷學生的姓名,年齡,性別,學號相等,那么返回true,這個也是符合自己的邏輯,但不能說明兩個類對象是相等的。

hashCode跟equals又是什么關系

默認的Object中的hashCode()是用的native層,得到一個hash值。

  public native int hashCode();
  1. 類沒有重寫hashCode方法,那么類對象equals比較的時候,跟hashCode沒有任何關系。

  2. 重寫了hashCode()方法。
    a. equals相等的兩個對象,hashCode()得到值一定相等
    b. hashCode值相等的兩個對象,equals不一定相等。

b)中的情況,可以從HashMap等使用hash值的集合中得到結果。當hash值相等的時候,說明發生了hash沖突。

重要的事情
在決定重寫hashCode()方法的時候,一定要做到規范,有含義,不然如果在對象添加到HashMap等集合中發生沖突的概率會大大提高。

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。