自定义排序规则 – Comparable和Comparator接口详解

Comparable接口与使用

接口定义

public interface Comparable <T> {
    public int compareTo(T o);
}

<T>限定参与比较的对象类型只能为T
compareTo()方法返回调用方和参数方的大小关系

调用对象 > 参数对象,返回值 > 0
调用对象 = 参数对象,返回值 = 0
调用对象 < 参数对象,返回值 < 0

案例实现

public class Person implements Comparable<Person> {

    private int age;
    private String name;

    public Person(int age, String name) {
        this.age = age;
        this.name = name;
    }

    @Override
    public int compareTo(Person o) {
        if (this.age != o.age) return Integer.compare(this.age, o.age);
        return String.CASE_INSENSITIVE_ORDER.compare(this.name, o.name);
    }

    public static void main(String[] args) {
        // test1
        Person a1 = new Person(24, "Alan");
        Person a2 = new Person(24, "Bob");
        System.out.println(a1.compareTo(a2));
        // test2
        Person b1 = new Person(24, "Cindy");
        Person b2 = new Person(20, "Dory");
        System.out.println(b1.compareTo(b2));
        // test3
        Person c1 = new Person(30, "Era");
        Person c2 = new Person(30, "Era");
        System.out.println(c1.compareTo(c2));
    }
}

使用要点

1)多个字段排序规则时涉及字段优先级,在第一顺位值相同时按照第二顺位值排序,依此类推

2)基本类型比较时,因涉及数据表示细节,建议使用包装类型的静态比较方法,详见下例

  • 整数减法发生下溢,如 \scriptsize -2147483648 - 1 = 2147483647

    public int compareTo(Object o) {
    return this.intVal - o.intVal;
    }
  • 浮点数强制类型转换整数时向偶数舍入,丢失运算结果符号位,如 \scriptsize (int)(0.03003-0.03005) = 0

    public int compareTo(Object o) {
    return (int) this.doubleVal - o.doubleVal;
    }
  • 浮点数比较时任一数为含有NAN

  • 浮点数比较时-0.0 < +0.0默认为false

参考资料

Bloch J. Effective Java[M]. Third Edition. 机械工业出版社, 2018.
Randal E.Bryant, David O’Hallaron. Computer Systems: A Programmer’s Perspective[M]. 3. 机械工业出版社, 2016.

发表回复

您的电子邮箱地址不会被公开。 必填项已用*标注

©2018-2024 Howell版权所有 备案号:冀ICP备19000576号