java物件比較
文章目錄
- java物件比較
- 元素的比較
- 類的比較
- 比較方法
- 重寫equals方法
- 基于Comparble介面類的比較
- 基于比較器比較基于比較器比較:Comparator介面
- 三種比較方式的對比
元素的比較
在java中,基本型別的物件可以直接比較大小,
public static void main(String[] args) {
int a=12;
int b=55;
System.out.println(a > b);
System.out.println(a == b);
System.out.println(a<b);
//字符的比較根據字符所對應ASCII值來比較大小
char ch1='a';
char ch2='b';
char ch3='c';
System.out.println(ch1>ch2);
System.out.println(ch1==ch2);
System.out.println(ch1<ch2);
boolean b1=true;
boolean b2=false;
System.out.println(b1==b2);
System.out.println(b1!=b2);
}

對于String類的比較可以參考我之前寫的博客:初識java的String類
類的比較
對于類的比較如果直接像元素比較一樣可能會造成編譯錯誤或者與預期效果的不一樣,
class Card{
public int rank;
public String suit;
public Card(int rank, String suit) {
this.rank = rank;
this.suit = suit;
}
}
public class Main{
public static void main(String[] args) {
Card c1 = new Card(1, "?");
Card c2 = new Card(2, "?");
Card c3 = c1;
// System.out.println(c1>c2);編譯報錯
System.out.println(c1==c2);//列印false,因為c1和c2指向的是不同物件
// System.out.println(c1<c2);編譯報錯
System.out.println(c1==c3);//列印false,因為c1和c2指向的是不同物件
}
}
從此編譯結果中我們可以發現,java中參考型別的變數不能直接按照> 或者< 方式進行比較,但確可以使用==符號進行比較?
原因:對于用戶自己實作定義的型別,都是默認為Object類,Object類提供了equal方法,此方法的比較規則是:無比較參考變數參考物件的內容,而是直接比較參考變數的地址,因此equal方法一般在使用的時候會被重寫
// Object中equal的實作,可以看到:直接比較的是兩個參考變數的地址
public boolean equals(Object obj) {
return (this == obj);
}
比較方法
在一些情況下,我們需要比較的是物件的內容,而不是比較物件的地址是否相同,則需要重寫比較方法,
重寫equals方法
class Card{
public int rank;
public String suit;
public Card(int rank, String suit) {
this.rank = rank;
this.suit = suit;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
// o如果是null物件,或者o不是Card的子類
if (o == null || !(o instanceof Card)) return false;
Card card = (Card) o;
return rank == card.rank && Objects.equals(suit, card.suit);
}
}
Public class Main{
public static void main(String[] args){
Card c1 = new Card(1, "?");
Card c2 = new Card(1, "?");
System.out.println(c1.equals(c2));
}
}
其equal方法實作如下:
- 如果這個類指向同一個物件則直接回傳true;
- 如果傳入的為慷訓者其物件型別不是Card,則回傳false
- 按照類的實作目標完成比較,這里只要花色和數值一樣,就認為是相同的牌
- 注意下呼叫其他參考型別的比較也需要 equals,例如這里的 suit 的比較
基于Comparble介面類的比較
Comparble是JDK提供的泛型的比較介面類,原始碼實作具體如下:
public interface Comparable<E>{
// 回傳值:
// < 0: 表示 this 指向的物件小于 o 指向的物件
// == 0: 表示 this 指向的物件等于 o 指向的物件
// > 0: 表示 this 指向的物件等于 o 指向的物件
public int compareTo(T o);
}
對于用戶自定義型別,如果按照大小與方式進行比較:可以在定義類的時候實作介面Comparable,并在類中重寫compareTo方法,
class Card implements Comparable<Card>{
public int rank;
public String suit;
public Card(int rank, String suit) {
this.rank = rank;
this.suit = suit;
}
@Override
public int compareTo(Card o) {
return this.rank-o.rank;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || !(o instanceof Card)) return false;
Card card = (Card) o;
return rank == card.rank && Objects.equals(suit, card.suit);
}
}
public class Main {
public static void main(String[] args) {
Card p = new Card(1, "?");
Card q = new Card(2, "?");
Card o = new Card(1, "?");
System.out.println(p.compareTo(o)); // == 0,表示牌相等
System.out.println(p.compareTo(q));// < 0,表示 p 比較小
System.out.println(q.compareTo(p));// > 0,表示 q 比較大
}
}

基于比較器比較基于比較器比較:Comparator介面
按照比較器方式進行比較,具體步驟如下:
- 戶自定義比較器類,實作Comparator介面
- 覆寫Comparator中的compare方法
class Card{
public int rank;
public String suit;
public Card(int rank, String suit) {
this.rank = rank;
this.suit = suit;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || !(o instanceof Card)) return false;
Card card = (Card) o;
return rank == card.rank && Objects.equals(suit, card.suit);
}
}
class CardComparator implements Comparator<Card>{
@Override
// 回傳值:
// < 0: 表示 o1 指向的物件小于 o2 指向的物件
// == 0: 表示 o1 指向的物件等于 o2 指向的物件
// > 0: 表示 o1 指向的物件等于 o2 指向的物件
public int compare(Card o1, Card o2) {
if (o1 == o2) {
return 0;
}
//判斷o1是否為空
if (o1 == null) {
return -1;
}
//判斷o2是否為空
if (o2 == null) {
return 1;
}
return o1.rank - o2.rank;
}
}
public class Main {
public static void main(String[] args) {
Card p = new Card(1, "?");
Card q = new Card(2, "?");
Card o = new Card(1, "?");
//定義比較器物件
CardComparator cmptor = new CardComparator();
// 使用比較器物件進行比較
// == 0,表示牌相等
System.out.println(cmptor.compare(p, o));
// < 0,表示 p 比較小
System.out.println(cmptor.compare(p, q));
// > 0,表示 q 比較大
System.out.println(cmptor.compare(q, p));
}
}

三種比較方式的對比
| 覆寫的方法 | 解釋說明 |
|---|---|
| Object.equals | 因為所有類都是繼承自 Object 的,所以直接覆寫即可,不過只能比較相等與否 |
| Comparable.compareTo | 需要手動實作介面,侵入性比較強,但一旦實作,每次用該類都有順序,屬于內部順序 |
| Comparator.compare | 需要實作一個比較器物件,對待比較類的侵入性弱,但對演算法代碼實作侵入性強 |
轉載請註明出處,本文鏈接:https://www.uj5u.com/ruanti/328123.html
標籤:其他
下一篇:在C 中使用回呼
