对对象的排序,可以通过以下两种方法:
- 实现Comparable接口,重写compareTo方法;
- Comparator比较器接口,重写compare方法;
Comparable接口
此接口只有一个方法
public int compareTo(T obj);
其中,T是泛型,需要指定具体的对象类型
接口中通过 x.compareTo(y)来比较x和y的大小
- x<y,返回负数;
- x=y,返回0;
- x>y,返回正数;
- 如果obj为null,则会抛出空指针异常
实现Comparable接口也需要指定具体的类型
public class Student implements Comparable<Student>{}
实现了该接口的类可以的数组或者List可以调用Arrays.sort()和Collections.sort()进行排序;
import java.util.Arrays;
public class Student implements Comparable<Student> {
int age;
String number;
Student(int age, String number) {
// super();
this.age = age;
this.number = new String(number);
}
Student() {
// super();
}
public String toString() {
return ("number:" + this.number + ",age:" + this.age);
}
@Override
public int compareTo(Student o1) {
// TODO Auto-generated method stub
return o1.age - this.age;
}
public static void main(String[] args) {
Student stu0 = new Student(22, "3150103299");
Student stu1 = new Student(21, "3170103299");
Student stu2 = new Student(23, "3160103298");
Student[] student = new Student[3];
student[0] = stu0;
student[1] = stu1;
student[2] = stu2;
System.out.println("排序前:");
for (Student stu : student)
System.out.println(stu.toString());
Arrays.sort(student);
System.out.println("------------");
System.out.println("排序后:");
for (Student stu : student)
System.out.println(stu.toString());
}
}
运行结果如图,实现了根据age进行排序:
Comparator比较器
Comparator 相当于一个比较器,作用和Comparable类似,也是使用Collections.sort() 和 Arrays.sort()来进行排序,也可以对SortedMap 和 SortedSet 的数据结构进行精准的控制,你可以不用实现此接口或者Comparable接口就可以实现次序比较。 TreeSet 和 TreeMap的数据结构底层也是使用Comparator 来实现。不同于Comparable ,比较器可以任选地允许比较null参数,同时保持要求等价关系。
Comparator比较器的方法,其中T为泛型,需要指定具体的类型;
int compare(T obj1, T obj2);
比较器实现Comparator方法的时候也需要指定具体类型
public class StudentComparator implements Comparator<Student>{}
实现了该接口的类可以的数组或者List可以调用Arrays.sort()和Collections.sort()进行排序;参数是数组或者list对象,以及比较器对象;
import java.util.Arrays;
import java.util.Comparator;
public class Student{
int age;
String number;
Student(int age, String number){
//super();
this.age = age;
this.number = new String(number);
}
Student(){
//super();
}
public String toString() {
return ("number:"+this.number+",age:"+this.age);
}
}
//构造比较器
class StudentComparator implements Comparator<Student>{
public int compare(Student stu1, Student stu2) {
return stu1.age - stu2.age;
}
}
public class Main{
public static void main(String[] args) {
Student stu0 = new Student(22,"3150103299");
Student stu1 = new Student(21,"3170103299");
Student stu2 = new Student(23,"3160103298");
Student[] student = new Student[3];
student[0]=stu0;
student[1]=stu1;
student[2]=stu2;
System.out.println("排序前:");
for(Student stu:student)
System.out.println(stu.toString());
Arrays.sort(student,new StudentComparator());
System.out.println("------------");
System.out.println("排序后:");
for(Student stu:student)
System.out.println(stu.toString());
}
}
运行结果如图:
两者区别:
- Comparable接口和类的耦合性高。就是说一个类实现了Comparable 接口,重写了compareTo()方法,那么它就可以被排序;
- 但是如果一个类没有实现Comparable接口,我们又无法对那个类进行改变,要实现排序的话,就可以使用Comparator接口;通过建立一个“该类的比较器”来进行排序(其实也是重新写一个类,这个类实现了Comparator接口,重写了compare()方法。
- compareTo()不接受null作为入参,compare()可以接受null作为入参,但要求保持等价关系