Java中Collections.sort()的使用

本文深入讲解Java中排序的实现方式,包括如何使对象可比较,使用Comparable接口与compareTo方法进行升序、降序排序,以及如何利用Comparator接口实现自定义排序逻辑。通过具体示例,如学生对象按年龄或ID排序,展示不同排序方法的应用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

在日常开发中,很多时候都需要对一些数据进行排序的操作。然而那些数据一般都是放在一个集合中如:Map ,Set ,List 等集合中。他们都提共了一个排序方法 sort(),要对数据排序直接使用这个方法就行,但是要保证集合中的对象是 可比较的。

怎么让一个对象是 可比较的,那就需要该对象实现 Comparable<T> 接口啦。然后重写里面的
compareTo()方法。我们可以看到Java中很多类都是实现类这个接口的 如:Integer,Long 等等。。。

假设我们有一个学生类,默认需要按学生的年龄字段 age 进行排序 代码如下:

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

    public Student(int id, int age, String name) {
        this.id = id;
        this.age = age;
        this.name = name;
    }
    @Override
    public int compareTo(Student o) {
        //降序
        //return o.age - this.age;
        //升序
        return this.age - o.age;        
    }
    @Override
    public String toString() {
        return "Student{" +
                "id=" + id +
                ", age=" + age +
                ", name='" + name + '\'' +
                '}';
    }
}


这里说一下重写的 public int compareTo(Student o){} 这个方法,它返回三种 int 类型的值: 负整数,零 ,正整数。
测试代码:

public static void main(String args[]){
        List<Student> list = new ArrayList<>();
        list.add(new Student(1,25,"关羽"));
        list.add(new Student(2,21,"张飞"));
        list.add(new Student(3,18,"刘备"));
        list.add(new Student(4,32,"袁绍"));
        list.add(new Student(5,36,"赵云"));
        list.add(new Student(6,16,"曹操"));
        System.out.println("排序前:");
        for (Student student : list) {
            System.out.println(student.toString());
        }
        //使用默认排序
        Collections.sort(list);
        System.out.println("默认排序后:");
        for (Student student : list) {
            System.out.println(student.toString());
        }
}


输出日志:

排序前:
Student{id=1, age=25, name='关羽'}
Student{id=2, age=21, name='张飞'}
Student{id=3, age=18, name='刘备'}
Student{id=4, age=32, name='袁绍'}
Student{id=5, age=36, name='赵云'}
Student{id=6, age=16, name='曹操'}
默认排序后:
Student{id=6, age=16, name='曹操'}
Student{id=3, age=18, name='刘备'}
Student{id=2, age=21, name='张飞'}
Student{id=1, age=25, name='关羽'}
Student{id=4, age=32, name='袁绍'}
Student{id=5, age=36, name='赵云'}




比较器的使用
这个时候需求又来了,默认是用 age 排序,但是有的时候需要用 id 来排序怎么办? 这个时候比较器 :Comparator 就排上用场了。

Comparator 的使用有两种方式:

Collections.sort(list,Comparator<T>);
list.sort(Comparator<T>);
其实主要是看 Comparator 接口的实现,重写里面的 compare 方法。代码如下:

//自定义排序1
Collections.sort(list, new Comparator<Student>() {
    @Override
    public int compare(Student o1, Student o2) {
        return o1.getId() - o2.getId();
    }
});


compare(Student o1, Student o2) 方法的返回值跟 Comparable<> 接口中的 compareTo(Student o) 方法 返回值意思相同。另一种写法如下:

//自定义排序2
list.sort(new Comparator<Student>() {
    @Override
    public int compare(Student o1, Student o2) {
        return o1.getId() - o2.getId();
    }
});
排序前:
Student{id=1, age=25, name='关羽'}
Student{id=2, age=21, name='张飞'}
Student{id=3, age=18, name='刘备'}
Student{id=4, age=32, name='袁绍'}
Student{id=5, age=36, name='赵云'}
Student{id=6, age=16, name='曹操'}
自定义排序后:
Student{id=1, age=25, name='关羽'}
Student{id=2, age=21, name='张飞'}
Student{id=3, age=18, name='刘备'}
Student{id=4, age=32, name='袁绍'}
Student{id=5, age=36, name='赵云'}
Student{id=6, age=16, name='曹操'}


--------------------- 
作者:宇智波为什么带土 
来源:优快云 
原文:https://blog.youkuaiyun.com/qq_23179075/article/details/78753136 
版权声明:本文为博主原创文章,转载请附上博文链接!

在1.8的文档中

      • public static <T> void sort(List<T> list,
                                    Comparator<? super T> c)
        根据指定的比较器引起的顺序对指定的列表进行排序。 列表中的所有元素必须使用指定的比较器相互比较 (即, c.compare(e1, e2)不能为ClassCastException中的任何元素e1e2 )。

        这种保证是稳定的 :等同的元素将不会被排序作为排序的结果。

        指定的列表必须是可修改的,但不能调整大小。

        实现注意事项:这个实现是一个稳定的,自适应的,迭代的mergeesort,当输入数组被部分排序时,需要比n lg(n)的比较少得多,同时在输入数组被随机排列时提供传统的mergeesort的性能。 如果输入数组几乎被排序,则实现需要大致n个比较。 临时存储要求从几乎排序的输入数组的小常数到随机排序的输入数组的n / 2对象引用。

        该实现在其输入数组中具有上升和下降的同等优势,并且可以在同一输入数组的不同部分中利用升序和降序。 它非常适合合并两个或多个排序的数组:简单地连接数组并排序生成的数组。

        该实现从Tim Peters的Python列表( TimSort )进行了改编 。 它使用Peter McIlroy的“乐观排序和信息理论复杂性”中的技术,在第四届ACM-SIAM离散算法研讨会论文集,pp 467-474,1993年1月。

        该实现将指定的列表转储到数组中,对数组进行排序,并在列表中迭代,从列表中的相应位置重新设置每个元素。 这样可以避免尝试将链表排序到目前为止的n 2 log(n)性能。

        参数类型

        T - 列表中对象的类

        参数

        list - 要排序的列表。

        c - 比较器来确定列表的顺序。 一个null值表示元素的自然排序应该被使用。

        异常

        ClassCastException - 如果列表包含使用指定的比较器不 相互比较的元素。

        UnsupportedOperationException - 如果指定的列表的list-iterator不支持 set操作。

        IllegalArgumentException - (可选)如果比较方发现违反Comparator合同

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值