题目描述
在数组中的两个数字,如果前面一个数字大于后面的数字,则这两个数字组成一个逆序对。输入一个数组,求出这个数组中的逆序对的总数P。并将P对1000000007取模的结果输出。 即输出P%1000000007
输入描述:
题目保证输入的数组中没有的相同的数字
数据范围:
对于%50的数据,size<=10^4
对于%75的数据,size<=10^5
对于%100的数据,size<=2*10^5
示例1
输入
1,2,3,4,5,6,7,0
输出
7
思路:若采用暴力搜索,时间复杂度为O(N^2),舍弃;采用归并排序的思路,对数组进行分治的划分,但不同于归并排序的是,在合并时选择从后往前,将较大的数放在合并数组的最后,若L[i]数组大于R[j]数组值,则说明存在j+1对逆序数。由于数据较大,因此在求值时需加入 %1000000007
代码:
class Solution {
public:
int merge(vector<int>& arr, vector<int> L, vector<int> R) {
int l = L.size();
int r = R.size();
int a = arr.size();
int i = l-1;
int j = r-1;
int k = a-1;
int res = 0;
while(i >= 0 && j >= 0) {
if(L[i] > R[j]) {
res += j + 1;
if(res > 1000000007)
res %= 1000000007;
arr[k--] = L[i--];
} else {
arr[k--] = R[j--];
}
}
while(i >= 0) {
arr[k--] = L[i--];
//res += j;
}
while(j >= 0) {
arr[k--] = R[j--];
}
return res;
}
int mergesort(vector<int>& arr) {
int n = arr.size();
if(n < 2) return 0 ;
int mid = n/2;
vector<int> L(mid);
vector<int> R(n - mid);
int i;
for(i = 0; i < mid; ++i) {
L[i] = arr[i];
}
for(i = mid; i < n; ++i) {
R[i - mid] = arr[i];
}
int lcnt = mergesort(L)%1000000007;
int rcnt = mergesort(R)%1000000007;
return (lcnt + rcnt + merge(arr, L, R))%1000000007;
}
int InversePairs(vector<int> data) {
int len = data.size();
int res = 0;
return mergesort(data)%1000000007;
//return res;
}
};