Java中Comparable和Comparator的使用方法

本文详细介绍了Java中Comparable和Comparator两种排序方式的使用方法,包括内置引用类型的比较、自定义数据排序等,并提供了具体代码实例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Java中Comparable和Comparator的使用方法


内置引用类型的比较

Comparable用法

这些类会继承Comparable接口,实现compareTo方法,通过该方法来实现对象之间比较。例如String:
String str="abc"; //如果其中一个是例外一个起始开始的子串,返回长度之差
String str2 ="abcd123";  //否则返回第一个不相等的unicode码之差
System.out.println(str.compareTo(str2));
str ="abc";
str2 ="aad";
System.out.println(str.compareTo(str2));

String内部继承Comparable接口,实现compareTo方法:

public int compareTo(String anotherString) {
        int len1 = value.length;
        int len2 = anotherString.value.length;
        int lim = Math.min(len1, len2);//获取两个字符串中最小的长度
        char v1[] = value;
        char v2[] = anotherString.value;

        int k = 0;
        while (k < lim) {
            char c1 = v1[k];
            char c2 = v2[k];
            if (c1 != c2) {
                return c1 - c2;
            }
            k++;
        }
        return len1 - len2;
    }

可用作引用类型集合的排序,封装一排序工具类Utils

public class Utils {
    /**
     * 容器排序 (使用泛型方法)
     */
    public static <T extends Comparable<T>> void sort(List<T> list){
        //第一步:转成数组
        Object[] arr =list.toArray();
        sort(arr);
        //第二步:改变容器中对应的值
        for(int i=0;i<arr.length;i++){
            list.set(i, (T)(arr[i]));
        }

    }

    /**
     * 数组排序 (使用泛型方法)
     */
    public static <T extends Comparable<T>> void sort(T[] arr){
        //从大到小排序 降序
        boolean sorted= true;
        int len =arr.length;
        for(int j=0;j<len-1;j++){ //趟数
            sorted =true; //假定有序
            for(int i=0;i<len-1-j;i++){ //次数
                if(((Comparable)arr[i]).compareTo(arr[i+1])<0){
                    T temp = arr[i];
                    arr[i] =arr[i+1];
                    arr[i+1] =temp;
                    sorted =false; //假定失败
                }
            }
            if(sorted){ //减少趟数
                break;
            }
        }
    }   
}

Comparator用法

我们还可以额外创建一个实现了Comparator接口的比较类来对集合进行排序,Comparator独立与实体类,便于应对各种排序规则。例如:

/**
 * 排序规则的业务类
 * @author Administrator
 *
 */
public class StrComparator  implements java.util.Comparator<String>{    
    /**
     * 按长度比较大小 
     * 正数 >
     * 负数 <
     * 0 ==
     */
    @Override
    public int compare(String o1, String o2) {
        int len1 =o1.length();
        int len2 =o2.length();      
        return -(len1-len2);
    }
}

封装排序工具类:

public class Utils {
    /**
     * List的排序+比较器
     * @param list
     * @param com
     */
    public static  <T> void sort(List<T> list,Comparator<T> com){
        //第一步:转成数组
        Object[] arr =list.toArray();
        sort(arr,com);
        //第二步:改变容器中对应的值
        for(int i=0;i<arr.length;i++){
            list.set(i, (T)(arr[i]));
        }
    }
    /**
     * 数组的排序 (降序)+Comparator接口
     * @param arr
     */
    public static <T> void sort(Object[] arr,Comparator<T> com){
        //从大到小排序 降序
            boolean sorted= true;
            int len =arr.length;
            for(int j=0;j<len-1;j++){ //趟数
                sorted =true; //假定有序
                for(int i=0;i<len-1-j;i++){ //次数
                    if(com.compare((T)arr[i], (T)arr[i+1])<0){
                        Object temp = arr[i];
                        arr[i] =arr[i+1];
                        arr[i+1] =temp;
                        sorted =false; //假定失败
                    }
                }
                if(sorted){ //减少趟数
                    break;
                }
            }
    }
}

使用方法:

list =new ArrayList<String>();
list.add("a");
list.add("abcd");
list.add("abc");
list.add("def");
Utils.sort(list,new StrComparator());
System.out.println(list);

使用Collections对容器的比较

//Comparator
List<String> list =new ArrayList<String>();
list.add("a");
list.add("abcd");
list.add("abc");
list.add("def");
Collections.sort(list,new StrComparator());
System.out.println(list);
//使用String默认排序
list =new ArrayList<String>();
list.add("a");
list.add("abcd");
list.add("abc");
list.add("def");
Collections.sort(list);
System.out.println(list);

自定义数据排序

Comparable

用Comparable方式实现新闻条目排序,直接上代码:
 public class News implements java.lang.Comparable<News>{
    //标题
    private String title;
    //点击量
    private int hits;
    //时间
    private Date publishTime;
    public News() {
    }

    public News(String title, int hits, Date pubTime) {
        super();
        this.title = title;
        this.hits = hits;
        this.publishTime = pubTime;
    }

    public String getTitle() {
        return title;
    }
    public void setTitle(String title) {
        this.title = title;
    }
    public int getHits() {
        return hits;
    }
    public void setHits(int hits) {
        this.hits = hits;
    }
    public Date getPubTime() {
        return publishTime;
    }
    public void setPubTime(Date pubTime) {
        this.publishTime = pubTime;
    }

    //首先按时间降序 +再按点击量升序+再按标题降序
    @Override
    public int compareTo(News o) {
        int result =0;
        //时间降序
        result =this.publishTime.compareTo(o.publishTime);
        if(0==result){
            //点击量 升序
            result =this.hits-o.hits;
            if(0==result){
                 //标题降序
                result=-this.title.compareTo(o.title);
            }
        }       
        return result;
    }
    @Override
    public String toString() {
        StringBuilder sb =new StringBuilder();
        sb.append("标题:").append(this.title);
        sb.append(",时间:").append(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(this.publishTime));
        sb.append(",点击量:").append(this.hits).append("\n");
        return sb.toString();
    }   
}

实现排序

List<News> news=new ArrayList<News>();
        news.add(new News("国产第十艘航母下水了",15000,new Date(System.currentTimeMillis()-1000*60*60)));
        news.add(new News("乐天集团倒闭了",16000,new Date()));
        news.add(new News("中国统一台湾",60000,new Date(System.currentTimeMillis()-1000*60*60)));
        System.out.println("排序前:"+news);        
        //排序
        //Collections.sort(news);   
        Utils.sort(news);
        System.out.println("排序后"+news);

Comparator

实体类

public class Goods {
    //商品名称
    private String name;
    //价格
    private double price;
    //销量
    private int salesNum;
    public Goods() {
    }
    public Goods(String name, double price, int salesNum) {
        super();
        this.name = name;
        this.price = price;
        this.salesNum = salesNum;
    }

    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public double getPrice() {
        return price;
    }
    public void setPrice(double price) {
        this.price = price;
    }
    public int getSalesNum() {
        return salesNum;
    }

    public void setSalesNum(int salesNum) {
        this.salesNum = salesNum;
    }
    @Override
    public String toString() {
        return "商品名称:"+name+",销量"+this.salesNum+",价格:"+this.price+"\n";
    }
}

实现Comparator接口,按销量排序的业务类 (降序)

public class GoodsSalesNumCompare implements java.util.Comparator<Goods> {

    @Override
    public int compare(Goods good1, Goods good2) {
        return -(good1.getSalesNum()-good2.getSalesNum());
    }

}

实现Comparator接口,按价格排序的业务类 (降序)

public class GoodsPriceCompare implements java.util.Comparator<Goods> {

    @Override
    public int compare(Goods good1, Goods good2) {
        return -(good1.getPrice()-good2.getPrice()>0?1:(good1.getPrice()==good2.getPrice()?0:-1));
    }

}

实现排序

List<Goods> list =new ArrayList<Goods>();
list.add(new Goods("iphone7plus",6300,2000));
list.add(new Goods("华为P10",3600,12000));
list.add(new Goods("小米MIX",3500,10000));
System.out.println("排序前:"+list);
Collections.sort(list,new GoodsSalesNumCompare());//商品按销售数量降序排序
//Collections.sort(list,new GoodsPriceCompare());//商品按价格降序排序
System.out.println("排序后:"+list);

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值