【发布时间】:2021-11-02 18:03:32
【问题描述】:
问题陈述
我正在尝试解决this 问题。
问题的简短摘要: 给定一个未排序的数组,求反转对的总数。 反转的定义: 如果 i arr[j]
,索引 i 和 j 形成一个有效的反转对我的做法:
- 我试图用分而治之来解决这个问题。 我将数组分成两部分,并递归求解每一部分。
- 递归调用完成后,每一半都应该排序,并且应该返回反转计数的个数。
当前数组的答案将是两半的答案之和 + 两半之间的反转对数。
请参阅此图以更好地了解此步骤:
图片来源:geeks for geeks
- 为了找到交叉反转的数量,我循环了第一个数组,对于每个元素,我在后半部分进行了二进制搜索,以获得确切元素的位置或第一个更大元素的位置(@987654324 @)。
虽然这种方法对我来说似乎是正确的并且通过了很少的测试用例,但它对一些隐藏的测试用例给出了错误的答案。
我需要帮助了解我的算法或实现是否存在任何缺陷。
我的实现:
static long inversionCount(long arr[], long N){
return solve(0, (int)N-1, arr);
}
static long solve(int l, int r, long[] arr){
if(l >= r) return 0;
int mid = l+(r-l)/2;
long countL = solve(l, mid, arr); //solve left half
long countR = solve(mid+1, r, arr); //solve right half
long countM = 0;
//count crossing inversions
for(int idx = l; idx <= mid; idx++){
int position = Arrays.binarySearch(arr, mid+1, r+1, arr[idx]);
if(position<0) position = -(position+1);
countM += position-mid-1;
}
Arrays.sort(arr, l, r);
return countM+countL+countR;
}
【问题讨论】:
标签: java arrays algorithm binary-search divide-and-conquer