对于下面的代码,我尝试根据枚举类型对bean进行排序。此bean的枚举类型也可以为null。
排序后的顺序应为:
A -> B -> C -> null.
运行以下代码后,元素的排序如下:
[A, A, C, B, B, null, C, null]
请帮忙
public class Bean implements Comparable<Bean> {
enum Type {
A, B, C
}
private Type type;
private int i;
private int j;
public Bean(Type type, int i, int j) {
this.type = type;
this.i = i;
this.j = j;
}
@Override
public int compareTo(Bean that) {
if (this.type == that.type) {
return 0;
}
if (this.type != null && that.type != null) {
if (this.type == type.A &&
that.type == type.B) {
return -1;
}
if (this.type == type.B &&
that.type == type.C) {
return -1;
}
if (this.type == type.A &&
that.type == type.C) {
return -1;
}
return 1;
}
return this.type == null ? 1 : -1;
}
@Override
public String toString() {
return "Bean{" + "type=" + (type != null ? type : "Unknown") + "}";
}
public static void main(String[] args) {
Bean b1 = new Bean(Type.B, 1, 1);
Bean b3 = new Bean(null, 3, 3);
Bean b2 = new Bean(Type.C, 2, 2);
Bean b0 = new Bean(Type.A, 0, 0);
Bean b4 = new Bean(Type.B, 4, 4);
Bean b5 = new Bean(null, 5, 5);
Bean b6 = new Bean(Type.C, 6, 6);
Bean b7 = new Bean(Type.A, 7, 7);
List<Bean> list = new ArrayList<>();
list.add(b1);
list.add(b3);
list.add(b2);
list.add(b0);
list.add(b4);
list.add(b5);
list.add(b6);
list.add(b7);
System.out.println(list);
System.out.println(new PriorityQueue<Bean>(list));
}
}
3条答案
按热度按时间k2fxgqgv1#
我看不出compareto有什么特别的问题,除了它的复杂性随着枚举数的增长而扩展。
问题是不同的:priorityqueue.tostring不会从队列中提取项,它只是打印底层的二进制堆结构。
请注意,二进制堆只是部分有序的。它确保了a[i]>a[2*i]和a[2*i+1],对于a[2*i]和a[2*i+1]的订购,不能事先说什么。
这个问题已经出现在stackoverflow中:priorityqueue.tostring元素顺序错误
ogsagwnx2#
你应该做的是:
然后
比较器应简单易读:
注意这是可能的,因为
Enum<E>
工具Comparable<E>
通过枚举的自然顺序这么做
将产生:
kknvjkwl3#
你没有考虑到所有可能的
this.type
以及that.type
. 你忘了:if (this.type == Type.B && that.type == Type.A)
if (this.type == Type.C && that.type == Type.A)if (this.type == Type.C && that.type == Type.B)
然而,有一个更简单的方法。所有枚举常量都是可比较的。它们的自然顺序是它们在源代码中声明的顺序。所以你可以做: