给定整数数组 nums 和整数 k,请返回数组中第 k 个最大的元素。
请注意,你需要找的是数组排序后的第 k 个最大的元素,而不是第 k 个不同的元素。
你必须设计并实现时间复杂度为 O(n) 的算法解决此问题。
示例 1:
输入: [3,2,1,5,6,4], k = 2
输出: 5
示例 2:
输入: [3,2,3,1,2,4,5,5,6], k = 4
输出: 4
代码:
class Solution {
public int findKthLargest(int[] nums, int k) {
quickSort(nums, 0, nums.length-1);
return nums[k-1];
}
// 双指针(指针对撞)快排,降序
public static void quickSort(int[] arr, int left, int right){
if (left > right){
// 不要忘记这里的结束条件
return;
}
// 重要:在第1个元素后面随机选1个元素与它交换位置,否则通过时间会很慢
// 因为测试用例中有极端测试用例,使得递归树加深
int randomIndex = left + new Random().nextInt(right - left + 1);
//swap交换(也可以抽取出来单独一个函数)
int t = nums[left];
nums[left] = nums[randomIndex];
nums[randomIndex] = t;
// swap(nums, randomIndex, left);
int i = left;
int j = right;
int mid = arr[left];
while(i != j){
while(i < j && arr[j] <= mid){
j--;
}
while(i < j && arr[i] >= mid){
i++;
}
// 此时左右指针均找到了大于或小于mid的值
// 交换这两个值使得循环能继续走下去
if(i<j){
int temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
}
//mid找到了自己的正确位置,通过交换放进去
arr[left] = arr[i];
arr[i] = mid;
//递归
quickSort(arr, left, i-1);
quickSort(arr, i+1, right);
}
}