Find the kth largest element in an unsorted array. Note that it is the kth largest element in the sorted order, not the kth distinct element.
For example,
Given [3,2,1,5,6,4] and k = 2, return 5.
Note:
You may assume k is always valid, 1 ≤ k ≤ array's length.
从无序数组中找到第k大的数
最简单的想法就是sort 然后返回第k个 无论是Arrays.sort 还是priority queue 时间复杂度nlog(n) n是数组元素的个数
实际上我们需要的是第k大的数 相当于是需要一个部分排序 k前面的比k大 k后面的比k小 至于k前面和后面元素的顺序 是无所谓的
『k前面的比k大 k后面的比k小』 看这个描述 很容易想到quick中的partition
public int findKthLargest(int[] nums, int k) {
k = nums.length - k;
int start = 0, end = nums.length-1;
while (start < end) {
int i = partition(nums, start, end);
if (i == k) break;
if (i > k) {
end = i-1;
} else {
start = i+1;
}
}
return nums[k];
}
public int partition(int[] nums, int left, int right) {
int small = left, big = left;
while (big < right) {
if (nums[big] < nums[right]) {
swap(nums, big, small++);
}
big++;
}
swap(nums, small, right);
return small;
}
private void swap(int[] nums, int i, int j) {
int tmp = nums[i];
nums[i] = nums[j];
nums[j] = tmp;
}
k = nums.length - k; //原题是想找第k大的数字 但是我们通常习惯的排序是从小到大
那么只要找第nums.length - k小的元素就可以了
然后选择数组的最后一个元素 对数组进行partition
返回的pivot 代表的是数组以哪个元素为中间值进行了分割 如返回3 表示数组以nums[3]为中间元素做了部分排序
nums[3]前面的元素小于3 nums[3]后面的元素大于3
然后判断pivot和k的关系
pivot>k pivot后面的元素都大于pivot 不用考虑了 从前面继续部分排序
pivot<k pivot后面的元素都小于pivot 不满足条件 继续对后面部分排序