Java中==和equals區別詳解

來源:互聯網
上載者:User

標籤:java   比較   

首先來說下兩種比較符的使用情境:
1、==是一般用來比較實值型別,比較兩個資料類型的值是否相等,例如:byte,shot,char,int,long,float,double,boolean,實值型別(還有對象引用)一般儲存在記憶體的棧中
2、equals用來比較複合資料型別,複合資料型別的變數在棧中儲存的是參考型別變數的地址,本身儲存在堆中。
當使用==比較複合資料型別時,比較的是他們在記憶體中的地址,使用同一個new出來的是相等,否則不相等。
JAVA當中所有的類都是繼承於Object這個基類的,在Object中的基類中定義了一個equals的方法,這個方法的初始行為是比較對象的記憶體地 址,但在一些類庫當中這個方法被覆蓋掉了,如String,Integer,Date在這些類當中equals有其自身的實現,而不再是比較類在堆記憶體中的存放地址了。
每new一個Object他們的記憶體位址不相同。
下面先貼一下String的equals的源碼看下:

/**     * Compares this string to the specified object.  The result is {@code     * true} if and only if the argument is not {@code null} and is a {@code     * String} object that represents the same sequence of characters as this     * object.     *     * @param  anObject     *         The object to compare this {@code String} against     *     * @return  {@code true} if the given object represents a {@code String}     *          equivalent to this string, {@code false} otherwise     *     * @see  #compareTo(String)     * @see  #equalsIgnoreCase(String)     */    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;    }

Object下即未被重寫過的equals方法:

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

比較實質:
在JAVA中利用”==”比較變數時,系統使用變數在”棧”中所存的值作為比較的依據。
基礎資料型別 (Elementary Data Type)在”棧”中存的是其內容值,而物件類型在”棧”中存的是地址,這些地址指向”堆”中的對象。
java.lang包中的Object類有public boolean equals(Object obj)方法,它比較兩個對象(hashcode)是否相等。
其它對象的equals方法僅當被比較的兩個引用指向的對象內容相同時,對象的equals()方法返回true。
總之,”==”和”!=”比較的是地址.也可認為”==”和”!=”比較的是物件控點;而equals()比較的是對象內容.或者說,,”==”和”!=”比較的是”棧”中的內容,而equals()比較的是”堆”中的內容.

publicclass Test{publicstaticvoid main(String[] args) {    String s1 ="null";    String s2 =new String("null");    System.out.println(s1==s2);//false    s2 = s2.intern();    System.out.println(s1==s2);//true}

(java.lang.String的intern()方法”abc”.intern()方法的傳回值還是字串”abc”,表面上看起來好像這個方 法沒什麼用處。但實際上,它做了個小動作:檢查字串池裡是否存在”abc”這麼一個字串,如果存在,就返回池裡的字串;如果不存在,該方法會 把”abc”添加到字串池中,然後再返回它的引用。
下面來看一個特殊的比較:

 Integer i1 = 127;  Integer j1 = 127;  System.out.println(i1 == j1); // true  Integer i2 = 128;  Integer j2 = 128;  System.out.println(i2 == j2);// false

以上是靠整型數的自動拆裝箱實現的,而兩者的結果卻不相同。
原因在於,在進行自動拆裝箱時,編譯器會使用Integer.valueof()來建立Integer執行個體。
先看一下源碼:

 public static Integer valueOf(int i) {        assert IntegerCache.high >= 127;        if (i >= IntegerCache.low && i <= IntegerCache.high)            return IntegerCache.cache[i + (-IntegerCache.low)];        return new Integer(i);    }

如果傳入的int在IntegerCache.low和IntegerCache.high之間,那就嘗試看前面的緩衝中有沒有打過包的相同的值,如果有就直接返回,否則就建立一個Integer執行個體。IntegerCache.low 預設是-128;IntegerCache.high預設是127.
註:如果要比較兩個對象的內容是否相同,盡量不使用== 或者!= 來比較,可以使用equal()來實現。

Java中==和equals區別詳解

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.