Java进阶(十五)常用类7: 比较器-Comparable或Comparator

    java中的对象正常情况下只能进行 == 或 != 的比较,不能使用 < 或 > 。在实际开发中,需要对多个对象进行排序,即比较对象的大小。如何实现?

    使用两个接口中的任何一个Comparable或Comparator。

一、Comparable(自然排序)

1.​​String、包装类​​​​

  •  已实现Comparable接口,重写compareTo()方法,并且排序方式为升序
  • 重写compareTo(obj)方法的规则:
    • 如果当前对象this>形参对象obj,则返回正整数;
    • 如果当前对象this<形参对象obj,则返回负整数;
    • 如果两个对象相等,返回0。
   @Test
    public void test1(){
        String[] arr=new String[]{"AA","DD","CC","BB"};
        Arrays.sort(arr);

        System.out.println(Arrays.toString(arr));//[AA, BB, CC, DD]

    }

2.自定义类

  • 让自定义类实现Comparable接口,在compareTo(obj)中指明如何排序。

  商品类代码:要求按照价格升序,再按商品名称降序

public class Goods implements Comparable {
    private String name;
    private double price;

   ...

    //指明商品比较大小的方式:按照价格升序,再按商品名称降序
    @Override
    public int compareTo(Object o) {

        if (o instanceof Goods) {
            Goods goods = (Goods) o;

            if (this.price > goods.price) {
                return 1;
            } else if (this.price < goods.price) {
                return -1;
            } else {
                return -this.name.compareTo(goods.name);
            }
        }
        throw new RuntimeException("传入的数据类型不一致");
    }
}

比较测试:

    @Test
    public void test2(){
        Goods[] arr = new Goods[5];
        arr[0]=new Goods("lenovoMouse",34);
        arr[1]=new Goods("dellMouse",43);
        arr[2]=new Goods("xiaomiMouse",12);
        arr[3]=new Goods("huaweiMouse",65);
        arr[4]=new Goods("microsoftMouse",65);

        Arrays.sort(arr);
        System.out.println(Arrays.toString(arr));
        //排序结果
//        [Goods{name='xiaomiMouse', price=12.0}, 
//        Goods{name='lenovoMouse', price=34.0}, 
//        Goods{name='dellMouse', price=43.0}, 
//        Goods{name='microsoftMouse', price=65.0},
//        Goods{name='huaweiMouse', price=65.0}]

    }

二、Comparator(定制排序)

1.背景

    当元素的类型没有实现Comparable接口,并且不方便修改代码,或者实现了Comparable接口的排序规则不适合当前的操作,那么可以考虑使用Comparator的对象来排序。

2.重写compare(Object o1,Object o2)方法

重写compare(Object o1,Object o2)方法的规则:
        如果o1大于o2,则返回正整数,
        如果o1小于o2,则返回负整数,
        如果两个对象相等,返回零。

3.String

    @Test
    public void test3() {
        String[] arr = new String[]{"AA", "DD", "CC", "BB"};
        Arrays.sort(arr, new Comparator() {

            //按字符串降序排
            @Override
            public int compare(Object o1, Object o2) {
                if (o1 instanceof String && o2 instanceof String) {
                    String s1 = (String) o1;
                    String s2 = (String) o2;
                    return -s1.compareTo(s2);
                }
                throw new RuntimeException("输入的数据类型不一致");
            }
        });

        System.out.println(Arrays.toString(arr));
        //排序结果:[DD, CC, BB, AA]
    }

4.自定义类

不用修改类的代码。要求产品名称升序,再按照价格降序

比较测试代码:

    @Test
    public void test4() {
        Goods[] arr = new Goods[6];
        arr[0] = new Goods("lenovoMouse", 34);
        arr[1] = new Goods("dellMouse", 43);
        arr[2] = new Goods("xiaomiMouse", 12);
        arr[3] = new Goods("huaweiMouse", 65);
        arr[4] = new Goods("microsoftMouse", 65);
        arr[5] = new Goods("huaweiMouse", 50);

        Arrays.sort(arr, new Comparator() {
            //指明商品比较大小的方式:产品名称升序,再按照价格降序。
            @Override
            public int compare(Object o1, Object o2) {
                if (o1 instanceof Goods && o2 instanceof Goods) {
                    Goods goods1 = (Goods) o1;
                    Goods goods2 = (Goods) o2;

                    if (goods1.getName().equals(goods2.getName())) {
                        return -Double.compare(goods1.getPrice(), goods2.getPrice());
                    } else {
                        return goods1.getName().compareTo(goods2.getName());
                    }
                }

                throw new RuntimeException("输入的数据类型不一致");
            }
        });
        System.out.println(Arrays.toString(arr));
        //排序结果
//        [Goods{name='dellMouse', price=43.0},
//        Goods{name='huaweiMouse', price=65.0},
//        Goods{name='huaweiMouse', price=50.0},
//        Goods{name='lenovoMouse', price=34.0},
//        Goods{name='microsoftMouse', price=65.0},
//        Goods{name='xiaomiMouse', price=12.0}]
    }

三、Comparable接口与Comparator的使用对比

  • Comparable接口的方式一旦指定,保证Comparable接口实现类的对象再任何位置都可以比较大小。
  • Comparator接口属于临时性的比较。
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值