hlo i'm always confuse why we use (a,b) -> a-b for sorting.
example-
Collections.sort(list, (a, b) -> { return (a[1] - b[1]); });
PriorityQueue MaxHeap = new PriorityQueue<>((a,b) -> a-b);
i'm really confused, i try to understand the flow of this statement by bebugging of code.
ArrayList<int[]> list = new ArrayList<>();
for (int i = 0; i < n; i ) {
list.add(new int[] { start[i], end[i] });
}
Collections.sort(list, (a, b) -> {
return (a[1] - b[1]);
});
int count = 1;
int[] x = list.get(0);
for (int i = 1; i < list.size(); i ) {
int[] res = list.get(i);
if (x[1] < res[0]) {
count = 1;
x = res;
}
}
return count;
}
if someone has a better way to understand this please help me.
CodePudding user response:
The goal of the lambda (a,b) -> a-b
is to produce a number that satisfies the Comparator
contract:
- if
a
less thanb
- return a negative result - if
a
equalsb
- return zero - if
a
greater thanb
- return a positive result.
The value returned by the Comparator
is used by sort
to compare pairs of elements (numbers) in the collection to decide which is bigger.
The problem is that a - b
doesn't work properly for Java integer types1. In some cases, a - b
will overflow and you will get a result with the wrong sign. For example, if a
is Integer.MIN_VALUE
and b
is a positive integer, then a - b
will be positive when it should be negative.
(This is a fairly common mistake, that even relatively experienced programmers make ... though hopefully, only once.)
By contrast, the Integer.compare(int, int)
method gives the correct answer ... for all possible arguments. So better (i.e. more correct) solutions would be:
Collections.sort(list, (a, b) -> Integer.compare(a[1], b[1]));
PriorityQueue<Integer> MaxHeap = new PriorityQueue<>(Integer::compare);
1 - In fact, for any kind of integer type where overflow doesn't trigger an exception of some kind. And for floating point types, there are different gotchas.