Below is the compare method of my comparator. I am not sure what is wrong.
I would like result in below formate.
Data: 1,3,0,1,0,4,6
Result: 1,1,3,4,6,0,0
Any help will be greatly appreciated
Comparator<Test> sortOrder = new Comparator<Test>() {
@Override
public int compare(Test d1, Test d2) {
Integer o1 = new Integer(d1.getVal() == null ? 0 : d1.getVal());
Integer o2 = new Integer(d2.getVal() == null ? 0 : d2.getVal());
if (o1 == 0) {
return 1;
}
if (o2 == 0) {
return -1;
}
return o1.compareTo(o2);
}
};
Set<Test> result = tests.stream().sorted(sortOrder).collect(Collectors.toCollection(LinkedHashSet::new));
Below is my exception:
java.lang.IllegalArgumentException: Comparison method violates its general contract!
at java.util.TimSort.mergeLo(TimSort.java:777)
at java.util.TimSort.mergeAt(TimSort.java:514)
at java.util.TimSort.mergeCollapse(TimSort.java:441)
at java.util.TimSort.sort(TimSort.java:245)
at java.util.Arrays.sort(Arrays.java:1512)
at java.util.stream.SortedOps$SizedRefSortingSink.end(SortedOps.java:348)
at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:482)
at java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:471)
at java.util.stream.ReduceOps$ReduceOp.evaluateSequential(ReduceOps.java:708)
at java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
at java.util.stream.ReferencePipeline.collect(ReferencePipeline.java:499)
Beyond the d1.getVal()
appearing twice typo (which may or may not exist in your actual code), you are violating the contract of Comparator
's compare
method, since sgn(compare(x,y)) != -sgn(compare(y,x))
if getVal()
is 0
for both of the compared Test
instances x
and y
.
You should either return 0
in this case or use another field to compare the two instances.
From the Javadoc:
The implementor must ensure that sgn(compare(x, y)) ==-sgn(compare(y, x)) for all x and y.