Java自定义比较器

前言:
我写了很多上层框架的知识,自以为会有很多人会很感兴趣,但发现其实看的人很少。于是我自己反思了一下为什么会这样,因为框架这种东西真的比较好学,随便买本书,或者看个什么什么视频,就比我写的博文好太多了,我思前想后很久,还是打算从那些容易忽略的细小知识出发,重新创建个javase模块,写点有质量的东西出来。

先举个调用java类库实现排序的例子:

    @Test
    public void tt(){
        List list =  new ArrayList();
        list.add(5);
        list.add(2);
        list.add(4);
        System.out.println(list);
        Collections.sort(list);
        System.out.println(list);
    }

相信有java基础的小伙伴都知道运行的结果,因为Collections.sort()方法将List排序了,结果如下:
在这里插入图片描述
但是,这就存在了一个问题,什么问题呢?当你给 List 添加的并不是数字,而是某个实体类对象,比如下面的实体类:

public class pojo {
    int no;
    String str;

    public pojo() {
    }

    public pojo(int no, String str) {
        this.no = no;
        this.str = str;
    }

    public int getNo() {
        return no;
    }

    public void setNo(int no) {
        this.no = no;
    }

    public String getStr() {
        return str;
    }

    public void setStr(String str) {
        this.str = str;
    }

    @Override
    public String toString() {
        return "pojo{" +
                "no=" + no +
                ", str='" + str + '\'' +
                '}';
    }
 }

存储这种对象的List ,idea还没运行就报错:
在这里插入图片描述
看到这个问题,就刚好能扯到我们本文的主题了。为什么会报错?因为sort方法只认识数字和字母,不知道怎么给你这个对象排序,解决方法就是自定义比较器了。
比较器有两种: Comparable 和 Comparator ,前者是侵入式的写法(会改变实体类的代码),后者是非侵入的,下面一一举例:

1.Comparable :

让pojo类实现Comparable接口,重写compareTo 方法:

public class pojo implements Comparable{
    int no;
    String str;

    public pojo() {
    }

    public pojo(int no, String str) {
        this.no = no;
        this.str = str;
    }

    public int getNo() {
        return no;
    }

    public void setNo(int no) {
        this.no = no;
    }

    public String getStr() {
        return str;
    }

    public void setStr(String str) {
        this.str = str;
    }

    @Override
    public String toString() {
        return "pojo{" +
                "no=" + no +
                ", str='" + str + '\'' +
                '}';
    }

    @Override
    public int compareTo(Object o) {
        pojo o1 = (pojo) o;
        return this.no > o1.no ? 1 : (this.no == o1.no? 0 : -1);
    }
}

注:当前值 > 比较值
返回 1:升序
返回 -1:降序
这样原来爆红的地方就没任何错误了:
在这里插入图片描述
运行结果:
在这里插入图片描述

2.Comparator:(博主推荐写法)

先自己写个类实现Comparator接口,重写里面的compare方法,如下:

public class CC implements Comparator<pojo> {

    @Override
    public int compare(pojo o1, pojo o2) {
//        return o1.no - o2.no; //根绝no 升序
//        return o2.no - o1.no;//根据no 降序
//        return o1.str.compareTo(o2.str);//根据str 升序
		  return -o1.str.compareTo(o2.str);//根据str 降序
        
    }
}

用的时候,只要给Collections.sort()方法后加上该类的实例:

    @Test
    public void test1(){
        List<pojo> pojos = new ArrayList<>();
        pojos.add(new pojo(1,"a"));
        pojos.add(new pojo(3,"b"));
        pojos.add(new pojo(2,"c"));
        Collections.sort(pojos,new CC());
        System.out.println(pojos);
    }

运行结果:

在这里插入图片描述

我解释一下为什么我推荐第二种写法,因为第一种写法违法了设计模式的单一职责原则,和迪米特法则,这两种法则我有在我另一篇博客提到----传送门,自己体会一下吧!

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

键盘歌唱家

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值