对于家庭作业问题,我需要编写一个Java方法来使用快速排序样式分区来查找数组中第k个最小的数字。我得到了partition()方法,我应该编写方法来获得第k个最小的数字。
问题是要求pivot始终是数组范围内最右边的元素。
我得到了以下内容:
public int partition(int left, int right, long pivot) {
int leftPtr = left - 1;
int rightPtr = right + 1;
while (true) {
while (leftPtr < right && array[++leftPtr] < pivot);
while (rightPtr > left && array[--rightPtr] > pivot);
if (leftPtr >= rightPtr)
break;
else
swap(leftPtr, rightPtr);
}
return leftPtr;
}
我已根据Wikipedia's pseudocode编写此方法:
public int kthSmallest(int left, int right, int k){
if(left >= right){
return array[left];
}
int pivotNewIndex = partition(left, right, array[right]);
int pivotDist = pivotNewIndex - left - 1;
if(pivotDist == k){
return array[pivotNewIndex];
} else if(k < pivotNewIndex){
return kthSmallest(k, left, pivotNewIndex - 1);
} else{
return kthSmallest(k - pivotDist, pivotNewIndex + 1, right);
}
}
但是当我用随机生成的整数数组调用kthSmallest()
时,大约一半的时间它会返回错误的值。例如:
array: [45, 60, 24, 82, 87, 79, 16, 32, 59, 83, 20, 2, 1,
50, 11, 79, 72, 32, 0, 48, 69, 74, 22, 6, 96]
expected result when k=4: 11
actual result when k=4: 87
我做错了什么?
答案 0 :(得分:1)
与维基百科伪代码相比,仔细查看对kthSmallest的递归调用。 k索引参数相对于哪个?
答案 1 :(得分:1)
您的递归调用的参数列表顺序错误。您正在查看的子阵列中的位置应该是第三个参数,而不是第一个参数。
答案 2 :(得分:0)
这是一个有效的解决方案(使用Java实现):http://blog.teamleadnet.com/2012/07/quick-select-algorithm-find-kth-element.html