Comparable和Comparator用法小结
概述
Comparable 接口和 Comparator 接口都是用来比较两个对象。一个类实现 Comparable 表示该类的对象之间可以比较;Comparator 则表示一个比较器,传入两个对象,返回比较结果。
它们的代码定义:
public interface Comparable<T> {
public int compareTo(T o);
}
@FunctionalInterface
public interface Comparator<T> {
int compare(T o1, T o2);
// ...
}
数组工具类和集合工具类中提供的 sort 排序方法就要求被排序的类实现 Comparable 接口或需要传入一个 Comparator 对象。
比较规则
compareTo 或 compare 都是返回一个 int 类型值。
对于 o1.compareTo(o2) 或 compare(o1, o2) ,返回不同 int 值时的意义:
- 返回 0 ,表示两个值相等。
- 返回 负数,表示 o1 会排在 o2 前面。即若是返回负数,o1、o2 位置不变。
- 返回 正数,表示 o1 会排在 o2 后面。即若是返回整数,o1、o2 位置交换。
根据这 3 个点,在定义比较规则时,从 “返回负数表示两个值位置不变” 这个点入手:
- 若是要按某个值升序排序,即返回负数的情况(o1,o2 位置不变)是 o1<o2 ,则应该
return o1-o2。这样当返回负数时,o1、o2 是升序的,位置不用变;返回正数,表示 o1 大于 o2,此时是降序的,应该交换位置。 - 而若是降序,返回负数的情况应是 o1>o2 ,则应该
return o2-o1。同理。
示例:
定义类:
class A implements Comparable<A>{
String name;
Integer num;
public A(String name, Integer num) {
this.name = name;
this.num = num;
}
// 排序时按 num 值递增进行
@Override
public int compareTo(A o) {
// 递增(升序),对应上面所说的 return o1-o2
return this.num - o.num;
}
@Override
public String toString() { return "A{" + "name='" + name + '\'' + '}'; }
}
将 A 的多个对象加入 List ,用 sort 方法进行排序:
public static void main(String[] args) {
A a1 = new A("a1", 1);
A a2 = new A("a2", 3);
A a3 = new A("a3", 2);
List<A> list = new ArrayList<>();
list.add(a1);
list.add(a2);
list.add(a3);
System.out.println(list);
Collections.sort(list);
System.out.println(list);
}
输出:
before sort: [A{name='a1'}, A{name='a2'}, A{name='a3'}]
after sort: [A{name='a1'}, A{name='a3'}, A{name='a2'}]
再看一个复杂一点的例子,对一个 nx2 的数组按第一个值升序排序,若第一个值相等,按第二个值倒序排序:
public static void main(String[] args) {
int[][] array = new int[][]{
{5,4},
{6,4},
{6,7},
{2,3}
};
System.out.println("before sort: ");
for (int[] ints : array) {
System.out.println(Arrays.toString(ints));
}
// (这里使用 Lambda 表达式, o1、o2 是一个一维数组)
// 第一个值相等时,第二个值倒序排序;否则第一个值升序排序
Arrays.sort(array, (o1, o2)-> o1[0] == o2[0] ? o2[1] - o1[1] : o1[0] - o2[0]);
System.out.println("\nafter sort: ");
for (int[] ints : array) {
System.out.println(Arrays.toString(ints));
}
}
before sort:
[5, 4]
[6, 4]
[6, 7]
[2, 3]
after sort:
[2, 3]
[5, 4]
[6, 7]
[6, 4]

浙公网安备 33010602011771号