Java函数:如何实现一个自定义的比较器来排序一个对象的列表?
Java中的列表是很常见的数据结构,常常需要对列表进行排序。Java提供了Collections.sort()方法来对列表进行排序,但是如果我们需要排序的对象是自定义的,那么就需要实现一个自定义的比较器来指定对象的比较规则。
Java中,实现自定义的比较器需要实现Comparator接口,该接口有一个比较方法compare(),用来指定两个对象之间的比较规则。该方法需要返回一个整数值,表示比较结果:
- 如果返回值为负数,表示第一个对象小于第二个对象;
- 如果返回值为零,表示两个对象相等;
- 如果返回值为正数,表示第一个对象大于第二个对象。
下面我们以一个Person类为例,来实现一个自定义的比较器:
public class Person {
private String name;
private int age;
public Person(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public int getAge() {
return age;
}
}
我们可以通过比较人的年龄来排序:
public class AgeComparator implements Comparator<Person> {
@Override
public int compare(Person o1, Person o2) {
return o1.getAge() - o2.getAge();
}
}
在这个比较器中,我们通过比较两个人的年龄大小来指定比较规则,年龄小的人排在年龄大的人之前。
使用该比较器对Person列表进行排序的代码如下:
List<Person> persons = new ArrayList<>();
persons.add(new Person("Tom", 18));
persons.add(new Person("John", 20));
persons.add(new Person("Sam", 15));
Collections.sort(persons, new AgeComparator());
for (Person p: persons) {
System.out.println(p.getName() + " " + p.getAge());
}
输出结果为:
Sam 15 Tom 18 John 20
从结果中可以看到,我们按照年龄从小到大排序了Person列表。
除了按照年龄排序,我们还可以按照名字字典序排序:
public class NameComparator implements Comparator<Person> {
@Override
public int compare(Person o1, Person o2) {
return o1.getName().compareTo(o2.getName());
}
}
使用该比较器排序的代码如下:
List<Person> persons = new ArrayList<>();
persons.add(new Person("Tom", 18));
persons.add(new Person("John", 20));
persons.add(new Person("Sam", 15));
Collections.sort(persons, new NameComparator());
for (Person p: persons) {
System.out.println(p.getName() + " " + p.getAge());
}
输出结果为:
John 20 Sam 15 Tom 18
从结果中可以看到,我们按照名字字典序排列了Person列表。
除了按照一个属性排序,我们也可以按照多个属性进行排序,如下所示:
public class MultiComparator implements Comparator<Person> {
@Override
public int compare(Person o1, Person o2) {
if (o1.getAge() == o2.getAge()) {
return o1.getName().compareTo(o2.getName());
} else {
return o1.getAge() - o2.getAge();
}
}
}
该比较器先按照年龄排序,如果年龄相同再按照名字排序。使用该比较器排序的代码如下:
List<Person> persons = new ArrayList<>();
persons.add(new Person("Tom", 18));
persons.add(new Person("John", 20));
persons.add(new Person("Sam", 15));
persons.add(new Person("John", 18));
Collections.sort(persons, new MultiComparator());
for (Person p: persons) {
System.out.println(p.getName() + " " + p.getAge());
}
输出结果为:
Sam 15 John 18 Tom 18 John 20
从结果中可以看出,我们按照年龄从小到大排序,如果年龄相同再按照名字字典序排序。John和Tom的年龄相同,但是John的名字字典序靠前,因此先输出John,后输出Tom。
总结:
Java提供了Collections.sort()方法对列表进行排序,但是对于自定义的类需要实现Comparator接口来指定比较规则。比较器需要实现compare()方法,返回值表示对象的比较结果。可以按照一个属性排序,也可以按照多个属性排序。
