【问题标题】:Comparison method violates its general contract! error with priority queue [duplicate]比较法违反其总约!优先级队列错误[重复]
【发布时间】:2017-05-08 07:06:25
【问题描述】:

我有一个优先级队列,它在线程内的 while(true) 循环中进行操作。在某些情况下,我想获取队列内容并将其排序到数组中。 我是这样做的:

Object[] array = sellQueues[0].toArray();
Arrays.sort(array);

这个优先级队列的比较方法如下:

public int compare(Order o1, Order o2) {
            try {
                if (o1.getBroker().getOrdersPriority() > o2.getBroker().getOrdersPriority())
                    return 1;
                else if (o1.getBroker().getOrdersPriority() < o2.getBroker().getOrdersPriority())
                    return -1;
                else {
                    if (o1.getBeginDate().before(o2.getBeginDate()))
                        return 1;
                    else if (o1.getBeginDate().after(o2.getBeginDate()))
                        return -1;
                    else {
                        if (o1.getBeginTime().before(o2.getBeginTime()))
                            return 1;
                        else if (o1.getBeginTime().before(o2.getBeginTime()))
                            return -1;
                        else
                            return 0;
                    }
                }
            } catch (NullPointerException e) {
                return 0;
            }
        }

由于某种原因,有时我会收到错误:

java.lang.IllegalArgumentException:比较方法违反了它的 总承包!

【问题讨论】:

  • 出于某种原因,有时我会收到错误消息....我们如何才能提供这样的描述性信息???
  • 我的眼睛是在走,还是在比较 o1.getBeginTime()ifelse if 中做同样的 .before 的其他人(即,其中一个不应该是.after())?

标签: java multithreading priority-queue


【解决方案1】:

比较器中的实现违反了其一般合同,因为: 假设订单 A,B,C 有相同的经纪人,A 有空开始日期,B 有开始日期 2017 年 1 月 1 日,C 的开始日期为 2018 年 1 月 1 日。那么

  1. A equals B 和 A equals C 通过比较器。
  2. 通过比较器,B 大于 C

因此 (2) 与 (1) 相矛盾。

为了更正实现,去掉NullPointerException的catch(捕捉RunTimeException的坏习惯),添加比较Order属性的方法,定义null的一致性比较。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-03-05
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多