public
class
ReversePairsCount {
static
void
merge(
int
[] arr,
int
low,
int
mid,
int
high) {
int
len1 = mid - low +
1
;
int
len2 = high - mid;
int
[] first =
new
int
[len1];
int
[] second =
new
int
[len2];
int
k = low;
for
(
int
i =
0
; i < len1; i++) {
first[i] = arr[k++];
}
k = mid +
1
;
for
(
int
i =
0
; i < len2; i++) {
second[i] = arr[k++];
}
int
i =
0
, j =
0
;
k = low;
while
(i < len1 && j < len2) {
if
(first[i] <= second[j]) {
arr[k++] = first[i++];
}
else
{
arr[k++] = second[j++];
}
}
while
(i < len1) {
arr[k++] = first[i++];
}
while
(j < len2) {
arr[k++] = second[j++];
}
}
static
int
countReversePairs(
int
[] arr,
int
low,
int
mid,
int
high) {
int
cnt =
0
;
int
j = mid +
1
;
for
(
int
i = low; i <= mid; i++) {
while
(i <= high && arr[i] >
2
* arr[j]) {
j++;
}
cnt += (j - (mid +
1
));
}
return
cnt;
}
static
int
mergeSort(
int
[] arr,
int
low,
int
high) {
int
cnt =
0
;
if
(low >= high) {
return
cnt;
}
int
mid = low + (high - low) /
2
;
cnt += mergeSort(arr, low, mid);
cnt += mergeSort(arr, mid +
1
, high);
cnt += countReversePairs(arr, low, mid, high);
merge(arr, low, mid, high);
return
cnt;
}
public
static
void
main(String[] args) {
int
[] arr = {
3
,
2
,
4
,
5
,
1
,
20
};
int
n = arr.length;
System.out.println(
"Reverse pairs are: "
+ mergeSort(arr,
0
, n -
1
));
}
}