题目
- 在数组中的两个数字,如果前面一个数字大于后面的数字,则这两个数字组成一个逆序对。输入一个数组,求出这个数组中的逆序对的总数P。并将P对1000000007取模的结果输出。 即输出P%1000000007
代码
- 归并排序的增强版本,根据左神的代码修改,以归并快排为基础
public class Solution {
long count=0;
public int InversePairs(int [] arr) {
if (arr == null || arr.length < 2) {
return 0;
}
mergeSort(arr, 0, arr.length - 1);
return count;
}
public static void mergeSort(int[] arr, int l, int r) {
if (l == r) {
return;
}
int mid = l + ((r - l) >> 1);
mergeSort(arr, l, mid);
mergeSort(arr, mid + 1, r);
merge(arr, l, mid, r);
}
public static void merge(int[] arr, int l, int m, int r) {
int[] help = new int[r - l + 1];
int i = 0;
int p1 = l;
int p2 = m + 1;
while (p1 <= m && p2 <= r) {
if(arr[p1]>arr[p2]){
help[i++]=arr[p2++];
count+=m-p1+1;
count=count>1000000007?(int)(count%1000000007):count;
}else
help[i++]=arr[p1++];
}
while (p1 <= m) {
help[i++] = arr[p1++];
}
while (p2 <= r) {
help[i++] = arr[p2++];
}
for (i = 0; i < help.length; i++) {
arr[l + i] = help[i];
}
}
}
public class Solution {
int count=0;
public int InversePairs(int [] array) {
if(array==null||array.length<=0) return 0;
mergeUp2Down(array,0,array.length-1);
return count;
}
public void mergeUp2Down(int [] a,int start,int end){
if(start>=end) return;
int mid=(end+start)>>1;
mergeUp2Down(a,start,mid);
mergeUp2Down(a,mid+1,end);
merge(a,start,mid,end);
}
public void merge(int [] a,int start,int mid,int end){
int[] temp=new int[end-start+1];
int i=start,j=mid+1,index=0;
while(i<=mid&&j<=end){
if(a[i]>a[j]) {
temp[index++]=a[j++];
count+=mid-i+1;
count=count>1000000007?count%1000000007:count;
}else
temp[index++]=a[i++];
}
while(i<=mid)
temp[index++]=a[i++];
while(j<=end)
temp[index++]=a[j++];
for(int k=0;k<temp.length;k++)
a[start+k]=temp[k];
}
}