-
Notifications
You must be signed in to change notification settings - Fork 1
/
kth-largest-element-in-an-array.py
150 lines (138 loc) · 3.95 KB
/
kth-largest-element-in-an-array.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
# coding=utf-8
"""
215. Kth Largest Element in an Array
"""
import heapq
class Solution(object):
def findKthLargest(self, nums, k):
"""
:type nums: List[int]
:type k: int
:rtype: int
最简单粗暴的方法
"""
if k > len(nums):
return -1
sorted_nums = sorted(nums, reverse=True)
return sorted_nums[k-1]
def findKthLargest1(self, nums, k):
"""
用最大堆做,python内置的heapq 的heapify是转为最小堆,
用了一个trick,取每个元素的相反数,得到最小堆,第一个pop的元素的相反数就是最大值
:param nums:
:param k:
:return:
"""
if k > len(nums):
return -1
nums = [-num for num in nums]
heapq.heapify(nums)
for i in range(k):
res = heapq.heappop(nums)
return -res
def findKthLargest2(self, nums, k):
"""
利用最小堆
:param nums:
:param k:
:return:
"""
n = len(nums)
if k > n:
return -1
min_heap = nums[:k]
heapq.heapify(min_heap)
for i in range(k, n):
if nums[i] > min_heap[0]:
heapq.heappop(min_heap)
heapq.heappush(min_heap, nums[i])
return min_heap[0]
def findKthLargest3(self, nums, k):
"""
使用快排的思想, 从大到小排序
:param nums:
:param k:
:return:
"""
if k > len(nums):
return -1
high = len(nums)-1
low = 0
partion = self.partion(nums, low, high)
if k-1 == partion:
return nums[partion]
if k-1 > partion:
k -= partion+1
return self.findKthLargest3(nums[partion+1:], k)
else:
return self.findKthLargest3(nums[:partion], k)
def partion(self, nums, low, high):
pivot = nums[low]
low_index = low
while low < high:
while high > low and nums[high] <= pivot:
high -= 1
while low < high and nums[low] >= pivot:
low += 1
if low < high:
nums[low], nums[high] = nums[high], nums[low]
nums[low_index], nums[low] = nums[low], nums[low_index]
return low
def findKthLargest4(self, nums, k):
"""
还利用快排的思想,但是不用递归了
:param nums:
:param k:
:return:
"""
if k > len(nums):
return -1
high = len(nums)-1
low = 0
while True:
partion = self.partion(nums, low, high)
if k-1 == partion:
return nums[partion]
if k-1 > partion:
low = partion+1
else:
high = partion-1
def findKthLargest5(self, nums, k):
"""
第k大就是第n+1-k小
:param nums:
:param k:
:return:
"""
import random
random.shuffle(nums)
k = len(nums) - k
low = 0
high = len(nums)-1
while True:
partion = self.partion1(nums, low, high)
if k == partion:
return nums[k]
if k > partion:
low = k + 1
else:
high = k - 1
def partion1(self, nums, low, high):
low_index = low
pivot = nums[low]
while low < high:
while high > low and nums[high] > pivot:
high -= 1
while low < high and nums[low] <= pivot:
low += 1
if low != high:
nums[low], nums[high] = nums[high], nums[low]
nums[low_index], nums[low] = nums[low], nums[low_index]
return low
def findKthSmallest(self, nums, k):
import heapq
heapq.heapify(nums)
res = []
for i in range(k):
res.append(heapq.heappop(nums))
return res