Java中Comparator的个人简单理解(升序降序)与使用

Java自定义排序返回值简单记忆理解

默认情况下:Java实现Comparator排序是升序,即自然排序
根据参数,返回值来判断是否交换

对于a,b两个参数(a在前,b在后)
jdk官方的升序基于:

< return -1
> return 1
= return 0

降序就是反过来

< return 1
> return -1
= return 0

简单记忆: 把-1理解为false,1理解为true(实际上底层源码并不是这样,实现原理参考dalao的博客,只是为了方便记忆使用)
如果要升序:那么a<b就是想要的顺序,所以return -1 ,false,不交换
如果要降序:那么a<b就是不想要的顺序,所以return 1,true,要交换
简而言之,返回1的时候进行位置交换

实践

分别对LinkedList和PriorityQueue进行测试

LInkedList

升序(默认情况)

LinkedList<Integer> list = new LinkedList<Integer>();

    list.add(2);
    list.add(9);
    list.add(7);
    list.add(5);
    list.add(3);
    list.add(1);
    list.add(0);

    Collections.sort(list, new Comparator<Integer>() {
            @Override
            public int compare(Integer o1, Integer o2) {
                if(o1>o2) return 1;
                else if(o1<o2) return -1;
                else return 0;
            }
        }
    );

    System.out.println(list);

结果
在这里插入图片描述
简化代码

//可以使用LinkedList继承自List的sort方法
list.sort(new Comparator<Integer>() {
            @Override
            public int compare(Integer o1, Integer o2) {
                if (o1 > o2) return 1;
                else if (o1 < o2) return -1;
                else return 0;
            }
        });

//中间的自定义比较可以用Integer中的compareTo函数代替
list.sort(new Comparator<Integer>() {
    @Override
    public int compare(Integer o1, Integer o2) {
        return o1.compareTo(o2);
    }
});

使用lambda表达式进一步简化

//lambda
list.sort((a,b) ->{
    if(a>b) return 1;
    else if(a<b) return -1;
    else return 0;
});
//lambda+compareTo()/compare()
list.sort((a,b) ->{
   return a.compareTo(b);
});
list.sort((a,b)->{
   return Integer.compare(a,b);
});
//lambda指向静态函数
list.sort(Integer::compareTo);
list.sort(Integer::compare);

直接调用Comparator中的naturalOrder()

list.sort(Comparator.naturalOrder());

降序

a,b交换一下顺序即可

直接使用lambda表达式+compare()/compareTo()

list.sort((a,b) ->{
    return b.compareTo(a);
});
list.sort((a,b) ->{
    return Integer.compare(b,a);
});

直接调用Comparator中的reverseOrder()

list.sort(Comparator.reverseOrder());

结果
在这里插入图片描述

PriorityQueue

优先队列默认结构为二叉小顶堆(层序遍历)
小顶堆:每个结点的值都小于或等于其左右孩子结点的值
大顶堆:每个结点的值都大于或等于其左右孩子结点的值

不清楚优先队列的同学建议先看一下这位dalao的博客

升序下的小顶堆(默认情况)

使用lambda表达式+compare()/compareTo()

PriorityQueue<Integer> queue = new PriorityQueue<>((a,b) ->{
    return Integer.compare(a,b);
    //return a.compareTo(b);
});
    queue.offer(1);
    queue.offer(9);
    queue.offer(5);
    queue.offer(6);
    queue.offer(8);

    System.out.println(queue);

结果
在这里插入图片描述
画图抽象出对应的二叉树结构
在这里插入图片描述
当然可以写成这三种形式

PriorityQueue<Integer> queue = new PriorityQueue<>(Integer::compare);
PriorityQueue<Integer> queue = new PriorityQueue<>(Integer::compareTo);
PriorityQueue<Integer> queue = new PriorityQueue<>(Comparator.naturalOrder());

降序下的大顶堆

排序规则改变之后,变成二叉大顶堆

PriorityQueue<Integer> queue = new PriorityQueue<>((a,b) ->{
    return Integer.compare(b,a);
    //return b.compareTo(a);
});

当然还可以写成

PriorityQueue<Integer> queue = new PriorityQueue<>(Comparator.reverseOrder());

结果
在这里插入图片描述
用画图抽象出对应的二叉树结构
在这里插入图片描述

总结

  • 自定义排序规则时,需要交换则返回1,不需要交换时返回-1,相等返回0。
  • 若使用lambda表达式,设定参数a,b初始顺序 与 调用函数传参顺序一致时 默认排序,即升序;位置相反时,则降序

2021/05/19

补充数组类型自定义排序

降序排序 数组

Integer[] arr = {1,2,3,4,5};
Arrays.sort(arr , (a,b) -> b-a);

当然还可以用Comparator这样写

Arrays.sort(arr, Comparator.reverseOrder());
Arrays.sort(arr, (a, b) -> b.compareTo(a));

注意:这里是必须要使用包装类型的,否则不能使用 sort 方法,因为 排序器只能对引用类型排序,而int,double等都是 primitive type (基本类型)就必须要包装成 Integer,Double 才可以

暂无评论

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇