java規範中equals方法特徵java
自反性(對於任何非空引用x, x.equals(x) 返回true;)this
對稱性(對於任何引用x, y, 當且僅當y.equals(x) 返回true, x.equals(y)返回true;)3d
傳遞性(對於任何引用x, y, z, 若x.equals(y)返回true, y.equals(z)返回true; 則 x.equals(z)返回true;)cdn
一致性(若x和y引用的對象沒有發生改變, 則反覆調用x.equals(y)應該返回一樣的結果.)對象
對任意非空引用x, x.equals(null) 返回false;blog
經過下面的例子掌握equals的用法繼承
package org.java.base.equals;內存
public class TestEquals {文檔
public static void main(String[] args) {字符串
/**
這裏使用構造方法Cat()在堆內存裏面new出了兩隻貓,
這兩隻貓的color,weight,height都是同樣的,
但c1和c2卻永遠不會相等,這是由於c1和c2分別爲堆內存裏面兩隻貓的引用對象,
裏面裝着能夠找到這兩隻貓的地址,但因爲兩隻貓在堆內存裏面存儲在兩個不一樣的空間裏面,
因此c1和c2分別裝着不一樣的地址,所以c1和c2永遠不會相等。
*/
Cat c1 = new Cat(1, 1, 1);
Cat c2 = new Cat(1, 1, 1);
System.out.println(「c1==c2的結果是:」+(c1==c2));//false
System.out.println(「c1.equals(c2)的結果是:」+c1.equals(c2));//false
}
}
class Cat {
int color, weight, height;
/**
定義一隻貓
@param color–顏色
@param weight–重量
@param height–高度
*/
public Cat(int color, int weight, int height) {
this.color = color;
this.weight = weight;
this.height = height;
}
}
輸出的結果以下:
c1==c2的結果是:false
c1.equals(c2)的結果是:false
c1指向一個對象,c2也指向一個對象,c1和c2裏面裝着的是這兩隻Cat對象在堆內存裏面存儲的地址,因爲這兩隻Cat對象分別位於不一樣的存儲空間,所以c1和c2裏面裝着的地址確定不相等,所以c1和c2這兩個引用對象也確定不相等。所以執行:「System.out.println(c1==c2);」打印出來的結果確定是false。所以你new出來了兩個對象,你放心,這兩個對象的引用永遠不同,同樣的話就會把其中一個給覆蓋掉了,這個可不成。c1是否是等於c2比較的是c1和c2這兩個引用裏面裝着的內容,由於new出來的兩個對象的它們的引用永遠不同,所以c1和c2這兩個引用的內容也永遠不同,所以c1永遠不可能等於c2。所以經過比較兩個對象的引用是永遠沒法使得兩個對象相等的,如出一轍的。
要想判斷兩個對象是否相等,不能經過比較兩個對象的引用是否相等,這是永遠都得不到相等的結果的,由於兩個對象的引用永遠不會相等,因此正確的比較方法是直接比較這兩個對象,比較這兩個對象的實質是否是同樣的,即這兩個對象裏面的內容是否是相同的,經過比較這兩個對象的屬性值是否相同而決定這兩個對象是否相等。
Object類提供了一個equals()方法來比較兩個對象的內容是否相同,所以咱們能夠採用這個方法去比較兩個對象是否在邏輯上「相等」。如:c1.equals(c2);這裏是調用從Object類繼承下來的equals()方法,經過查閱API文檔獲得Object類裏的equals方法的定義以下:
public boolean equals(Object obj)
在Object這個類裏面提供的Equals()方法默認的實現是比較當前對象的引用和你要比較的那個引用它們指向的是不是同一個對象,即和「c1==c2」這種寫法是同樣的,「c1.equals(c2)」與「c1==c2」是徹底等價的。所以直接使用繼承下來的equals()方法也是沒法直接比較兩個對象的內容是否相同的,爲此,咱們必須得重寫equals()方法,改變這個方法默認的實現。
public boolean equals(Object obj){
if (obj==null){
return false;
}
else{
/**
instanceof是對象運算符。
對象運算符用來測定一個對象是否屬於某個指定類或指定的子類的實例。
對象運算符是一個組合單詞instanceof。
該運算符是一個雙目運算符,其左邊的表達式是一個對象,右邊的表達式是一個類,
若是左邊的對象是右邊的類建立的對象,則運算結果爲true,不然爲false。
*/
if (obj instanceof Cat){
Cat c = (Cat)obj;
if (c.color==this.color && c.weight==this.weight && c.height==this.height){
return true;
}
}
}
return false;
}
這一次獲得的結果就與上次沒有重寫equals()方法時獲得的結果就不同了:
c1==c2的結果是:false
c1.equals(c2)的結果是:true
「System.out.println(c1 == c2);」打印出來的結果依然是false,由於這裏是比較兩個對象的引用裏面的內容,這兩個引用裏面的內容固然不相等,並且永遠不會相等,因此打印出來的結果確定是false。
「System.out.println(c1.equals(c2));」打印出來的結果爲true,由於咱們在Cat類裏面重寫了equals()方法,改變了這個方法默認的實現,咱們把方法的實現改成只要這個兩個對象是真的存在,而且都是貓,而且它們的顏色(color),身高(height)和體重(weight)都相同,那麼這兩隻貓在邏輯上就是如出一轍的,是徹底相同的兩隻貓,即這兩隻貓是「相等」的。因此這裏打印出來的結果是true。
1.3.如何比較兩個字符串對象是否相等?
在String類裏面是這樣重寫equals()方法的實現的:用當前的這個字符串對象和指定的字符串對象比較,指定的字符串對象不能爲空而且這個對象的字符序列和當前這個字符串對象的字符串序列同樣,若是這些條件都知足,那麼這兩個字符串對象就是相等的。
總結:比較兩個對象是否相等,咱們採用equals()方法,判斷兩個對象是否相等的條件是由咱們重寫equals()方法的實現後定義的,這樣就能夠比較靈活地使用equals()方法在不一樣的類裏面比較位於同一類下的兩個對象是否相等了。
有興趣的朋友能夠加947405150 一塊兒吹b交流!