Java Comparable 與 Comparator

在收集對(duì)象之后,對(duì)象的排序是經(jīng)常需要用到的操作。但我們不需要親自實(shí)現(xiàn)各種排序算法,java.util.Collections提供了sort方法,List作為一種collections,而且存在索引,所以可以調(diào)用sort方法進(jìn)行排序。顯然,必須具有索引,才能進(jìn)行排序。

package Collection;

import java.util.*;

public class Sort {

    public static void main(String[] args) {
        List numbers = Arrays.asList(1,2,3,4,5,6,8,7,12,1);
        Collections.sort(numbers);
        System.out.println(numbers);
    }

}

執(zhí)行結(jié)果是將數(shù)據(jù)進(jìn)行由小到大的排序:

Paste_Image.png

但如果是下面這個(gè)例子呢?

package Collection;

import java.util.Arrays;
import java.util.Collections;
import java.util.List;

public class Sort2 {
    
    

    public static void main(String[] args) {
        List accounts = Arrays.asList(
                new Account("Justin", "X1234", 1000),
                new Account("Monica", "X5678", 500),
                new Account("Irene", "X2468", 200)
        );
        Collections.sort(accounts);
        System.out.println(accounts);

    }

}

class Account {
    private String name;
    private String numbers;
    private double balance;
    
    Account(String name,String numbers,double balance) {
        this.name = name;
        this.numbers = numbers;
        this.balance = balance;
    }
    
    @Override
    public String toString() {
        return String.format("Account(%s,%s,%d)", name,numbers,balance);
    }
}

執(zhí)行之后,我們發(fā)現(xiàn)程序報(bào)錯(cuò)了:

Paste_Image.png

錯(cuò)誤信息是,我們定義的Account無法轉(zhuǎn)換為Comparable類型。
顯然,這就是說明collection的sort方法必須室友comparable類的對(duì)象進(jìn)行調(diào)用,因?yàn)槲覀兗热灰獙?duì)對(duì)象進(jìn)行排序,顯然就要告訴程序如何對(duì)對(duì)象進(jìn)行排序,是按什么排?這就需要去實(shí)現(xiàn)comparable接口,這是一個(gè)形容詞,也就是表明,對(duì)象是可比較大小的,那自然就可以排序了。這個(gè)接口有一個(gè)comparaTo的方法,必須返回大于0,小于0或者等于0的數(shù),這就是sort的排序方式。

所以接下來我們就改寫上面的例子,使其更具賬戶余額的大小進(jìn)行排序。

package Collection;

import java.util.Arrays;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;

public class Sort3 {
    
    

    public static void main(String[] args) {
        List accounts = Arrays.asList(
                new Account2("Justin", "X1234", 1000),
                new Account2("Monica", "X5678", 500),
                new Account2("Irene", "X2468", 200)
        );
        Collections.sort(accounts);
        System.out.println(accounts);

    }

}

class Account2 implements Comparable<Account2> {
    private String name;
    private String numbers;
    private double balance;
    
    Account2(String name,String numbers,double balance) {
        this.name = name;
        this.numbers = numbers;
        this.balance = balance;
    }
    
    @Override
    public String toString() {
        return String.format("Account(%s,%s,%f)", name,numbers,balance);
    }

    

    @Override
    public int compareTo(Account2 o) {
        // TODO Auto-generated method stub
        
        return (int) (this.balance - o.balance);
    }
    
    
}

Paste_Image.png

這就根據(jù)銀行余額的值返回了正確的結(jié)果,所以我們知道,要對(duì)對(duì)象進(jìn)行排序,首先一定要是可比較大小的,不然怎么排序,要可比較大小,就需要繼承實(shí)現(xiàn)comparable接口,實(shí)現(xiàn)里面的comparaTo方法,定義排序的規(guī)則。

那么疑問來了,為什么我們的第一個(gè)例子,可以正確的對(duì)integer進(jìn)行排序呢?
那是因?yàn)閖dk已經(jīng)默認(rèn)幫integer實(shí)現(xiàn)了comparable接口。
但問題還是來了,如果我們希望integer的排序方法由大到小呢?那怎么辦,難道我們需要重新去實(shí)現(xiàn)integer的comparable接口的comparaTo方法?顯然這是不現(xiàn)實(shí)的,因?yàn)檫@些都是在jdk默認(rèn)提供的api里,這時(shí)候,我們發(fā)現(xiàn),還有一個(gè)comparator接口。

Collections的sort()方法有另一個(gè)重載的版本,可接受java.util.Comparator接口的的實(shí)例對(duì)象,如果你使用這個(gè)版本,排序方式就將根據(jù)Comparator的compare()定義來決定。

package Collection;

import java.util.Arrays;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;

public class Sort5 {

    public static void main(String[] args) {
        // TODO Auto-generated method stub
        List<String> words = Arrays.asList("B", "X", "A", "M", "F", "W", "O");
        Collections.sort(words, new Comparator<String>() {

            @Override
            public int compare(String o1, String o2) {
                // TODO Auto-generated method stub
                return -o1.compareTo(o2);
            }
            
        });
        
        System.out.println(words);
    }

}
Paste_Image.png

在Java中,根據(jù)順序有關(guān)的行為要么是實(shí)現(xiàn)了comparable接口,要么就是實(shí)現(xiàn)了comparator接口類型。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 從三月份找實(shí)習(xí)到現(xiàn)在,面了一些公司,掛了不少,但最終還是拿到小米、百度、阿里、京東、新浪、CVTE、樂視家的研發(fā)崗...
    時(shí)芥藍(lán)閱讀 42,793評(píng)論 11 349
  • 1. Java基礎(chǔ)部分 基礎(chǔ)部分的順序:基本語法,類相關(guān)的語法,內(nèi)部類的語法,繼承相關(guān)的語法,異常的語法,線程的語...
    子非魚_t_閱讀 34,673評(píng)論 18 399
  • java中我們要實(shí)現(xiàn)集合元素的比較和排序有兩種方法。一種是讓集合中的元素去實(shí)現(xiàn)Comparable接口,另一種是則...
    趙仝閱讀 751評(píng)論 0 1
  • java筆記第一天 == 和 equals ==比較的比較的是兩個(gè)變量的值是否相等,對(duì)于引用型變量表示的是兩個(gè)變量...
    jmychou閱讀 1,647評(píng)論 0 3
  • 一、基本數(shù)據(jù)類型 注釋 單行注釋:// 區(qū)域注釋:/* */ 文檔注釋:/** */ 數(shù)值 對(duì)于byte類型而言...
    龍貓小爺閱讀 4,449評(píng)論 0 16

友情鏈接更多精彩內(nèi)容