自然排序Comparable与比较器排序Comparator

有的时候我们需要按照自定义的方式比较两个对象的大小,java中提供了两个接口, java.lang.Comparable 和 java.util.Comparator
自然排序Comparable

让这个两个需要比较对象的类实现Comparable接口。

1.要让一个类使用排序服务必须让它实现comparaeTo方法,这是因为需要向sort方法提供比较方式。

2.任何实现Comparable接口的类都需要包含compareTo方法。

    @Override
    public int compareTo(Student o) {
        return this.id - o.id;
    }

注意这里的相减技巧不适用于浮点值

比较器排序

比较器是实现了Comparator接口的类的实例,我们需要这个实例来调用compare方法完成比较的功能

  @Override
            public int compare(Student o1, Student o2) {
                return o1.getId() - o2.getId();
            }

从小到大排序
//return o1.getId() - o2.getId();
从大到小排序
//return o2.getId() - o1.getId();
二者的区别:

1.使用比较器的优点是可以将比较算法和具体的类分离,降低类之间的耦合。

2.有的时候需要对同一对象进行多种不同方式的排序,这点自然排序Comparable不能实现。就比如前面我们对一组student对象按照id进行排序,但是在某些情况下又需要按照age进行排序。

3.对一个字符串数组排序,因为String类实现了Comparable,而且String.compareTo方法是根据字典顺序比较字符串。那么如果我们需要按长度递增的顺序对字符串进行排序,而不是按字典顺序进行排序。肯定不能让String类用两种不同的方式实现compareTo方法,我们也不应该去修改String类。这个时候就需要用到比较器。

总结:自然排序Comparable是类在创建的时候就规定了类的比较的特性,而比较器Comparator是在具体的应用过程中我们根据需求创建一个工具类来完成比较,相比之下比较器的使用更加灵活,不会改变这个类本身,减低了耦合度。

举例:
下面以Student按照id从小到大排序分别用两种方式实现:
方法1:实现Comparable接口


import java.util.*;

public class ComparableTest {
    public static void main(String[] args) {
        List<Student> list = new ArrayList<>();
        Student student1 = new Student(1, "student1");
        Student student2 = new Student(2, "student2");
        Student student3 = new Student(3, "student3");
        list.add(student1);
        list.add(student3);
        list.add(student2);
        //对list集合中的学生对象按照id从小到大排序
        //Collections类中的sort方法可以对实现了List接口的集合进行排序,这个方法假定列表元素实现了Comparable接口
        Collections.sort(list);
        System.out.println(list);

    }
}

class Student implements Comparable<Student> {
    private int id;
    private String name;

    public Student(int id, String name) {
        this.id = id;
        this.name = name;
    }

    @Override
    public String toString() {
        return "Student{" +
                "id=" + id +
                ", name='" + name + '\'' +
                '}';
    }

    @Override
    public int compareTo(Student o) {
        return this.id - o.id;
    }
}

方法2:使用比较器(比较器是实现了Comparator接口的类的实例)

import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;

public class ComparatorTest {
    public static void main(String[] args) {
        List<Student> list = new ArrayList<>();
        Student student1 = new Student(1, "student1");
        Student student2 = new Student(2, "student2");
        Student student3 = new Student(3, "student3");
        list.add(student1);
        list.add(student3);
        list.add(student2);
        //对list集合中的学生对象按照id从小到大排序
        list.sort(new Comparator<Student>() {
            @Override
            public int compare(Student o1, Student o2) {
                return o1.getId() - o2.getId();
            }
        });
        System.out.println(list);

    }
}

class Student {
    private int id;
    private String name;

    public Student(int id, String name) {
        this.id = id;
        this.name = name;
    }

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "Student{" +
                "id=" + id +
                ", name='" + name + '\'' +
                '}';
    }


}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值