zoukankan      html  css  js  c++  java
  • 整数排序中的坑

    Java中对集合或者数组排序一般有两个方法,类实现Comparable 接口或者 排序时使用定制化接口 Comparator。
    以TreeSet为例,日常写法:

     Set<Integer> sets = new TreeSet<>(new Comparator<Integer>() {
        @Override
        public int compare(Integer o1, Integer o2) {
            return o2 == o1 ? 0 : o2 > o1 ? 1 : -1;
        }
    });
    sets.add(1);
    sets.add(-1);
    sets.add(100);
    System.out.println(Arrays.toString(sets.toArray(new Integer[]{})));
    //[100, 1, -1]
    

    关于上面的写法,还有一种变种,就是改成o2-o1,似乎没有问题,看源码,使用Comparator的时候,是按照正负进行判断的

    坑来了

    看例子

    Set<Integer> sets = new TreeSet<>(new Comparator<Integer>() {
        @Override
        public int compare(Integer o1, Integer o2) {
            return o2-o1;
        }
    });
    sets.add(1);
    sets.add(-1);
    sets.add(Integer.MIN_VALUE);
    System.out.println(Arrays.toString(sets.toArray(new Integer[]{})));
    [-2147483648, 1, -1]
    

    是不是不是预想的结果了,-2147483648成了最大值。

    原因:

    很简单,做个测试 -2147483648 -1 = ? 答案是 2147483648。
    数字在边界处会溢出,比如 2147483648+1=-2147483648

    最佳实践:

    使用Comparator接口工作时,一定使用比较将结果控制在-1 ,0 1 三个值,保证结果稳定,如果使用数字加减排序,有可能因为有数字溢出导致结果异常。

  • 相关阅读:
    Tomcat基于MSM+Memcached实现Session共享
    Zabbix简介及安装
    redis简介
    Ansible详解(二)
    Ansible详解(一)
    WAMP3.1.10/Apache 设置站点根目录
    最长回文子串--轻松理解Manacher算法
    一篇文章彻底了解Java垃圾收集(GC)机制
    java内存模型详解
    Java中23种设计模式--超快速入门及举例代码
  • 原文地址:https://www.cnblogs.com/jason0529/p/14028980.html
Copyright © 2011-2022 走看看