problem
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.
solution1
直接对用数组进行排序,取倒数第k个元素即为所求。
class Solution(object):
def findKthLargest(self, nums, k):
nums.sort()
return nums[-k]
时间复杂度为 O(nlog(n))
solution2
使用大顶堆对原来的list建堆,然后pop出第k个即为我们所求。
但是python中的heapq只能实现小顶堆,这里我们可以转而求第n-k+1小的元素,或者将原来的元素对变为其相反数,建堆然后返回第k小的数的相反数(不等式乘负数变号)。
更多关于模块heapq参考heapq文档
class Solution(object):
def findKthLargest(self, nums, k):
"""
:type nums: List[int]
:type k: int
:rtype: int
"""
import heapq
return heapq.nlargest(k, nums)[-1]
solution3
这种算法类似于快排的分治算法,也是选择一个pivot,使得数组左边的元素小于pivot,右边的大于pivot,如果pivot不是第k大则在左边或右边进行寻找。
这个是用python实现的, 空间复杂度为
O(n)
class Solution(object):
def findKthLargest(self, nums, k):
"""
:type nums: List[int]
:type k: int
:rtype: int
"""
pivot=random.choice(nums)
num1,num2=[],[]
for i in nums:
if i>pivot:
#nums1是大于pivot的元素
num1.append(i)
if i<pivot:
num2.append(i)
if k<=len(num1):
return self.findKthLargest(num1, k)
elif k>len(nums)-len(num2):
#第k大不在nums1和pivot里面
return self.findKthLargest(num2, k-(len(nums)-len(num2)))
else:
return pivot
空间复杂度为 O(1) 的Java代码:
public class Solution {
public int findKthLargest(int[] nums, int k) {
int start = 0, end = nums.length - 1, index = nums.length - k;
while (start < end) {
int pivot = partion(nums, start, end);
if (pivot < index) start = pivot + 1;
else if (pivot > index) end = pivot - 1;
else return nums[pivot];
}
return nums[start];
}
private int partion(int[] nums, int start, int end) {
int pivot = start, temp;
while (start <= end) {
while (start <= end && nums[start] <= nums[pivot]) start++;
while (start <= end && nums[end] > nums[pivot]) end--;
if (start > end) break;
temp = nums[start];
nums[start] = nums[end];
nums[end] = temp;
}
temp = nums[end];
nums[end] = nums[pivot];
nums[pivot] = temp;
return end;
}
}