-
Notifications
You must be signed in to change notification settings - Fork 35
Expand file tree
/
Copy path480_sliding_window_median.py
More file actions
102 lines (74 loc) · 2.34 KB
/
480_sliding_window_median.py
File metadata and controls
102 lines (74 loc) · 2.34 KB
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
import heapq
class HashHeapq:
def __init__(self):
self.__heap = []
def __repr__(self):
return repr(self.__heap)
def __len__(self):
return len(self.__heap)
def __bool__(self):
return bool(self.__heap)
def push(self, val):
heapq.heappush(self.__heap, val)
def pop(self):
if not self.__heap:
return
return heapq.heappop(self.__heap)
def remove(self, val):
if not self.__heap:
return
i = 0
n = len(self.__heap)
while i < n and self.__heap[i] != val:
i += 1
if i == n:
return
if i == n - 1:
self.__heap.pop()
else:
self.__heap[i] = self.__heap[-1]
self.__heap.pop()
heapq._siftup(self.__heap, i)
heapq._siftdown(self.__heap, 0, i)
def top(self):
if not self.__heap:
return
return self.__heap[0]
class Solution:
def medianSlidingWindow(self, nums, k):
"""
:type nums: List[int]
:type k: int
:rtype: List[float]
"""
ans = []
if not nums or k <= 0 or len(nums) < k:
return ans
self.minheap = HashHeapq()
self.maxheap = HashHeapq()
for i in range(len(nums)):
# remove nums[i - k]
if i >= k:
if self.minheap and nums[i - k] >= self.minheap.top():
self.minheap.remove(nums[i - k])
else:
self.maxheap.remove(- nums[i - k])
# add nums[i]
if self.minheap and nums[i] >= self.minheap.top():
self.minheap.push(nums[i])
else:
self.maxheap.push(- nums[i])
# get median
if i >= k - 1:
ans.append(self.get_median())
return ans
def get_median(self):
if not self.minheap and not self.maxheap:
return 0.0
while len(self.minheap) > len(self.maxheap) + 1:
self.maxheap.push(- self.minheap.pop())
while len(self.maxheap) > len(self.minheap):
self.minheap.push(- self.maxheap.pop())
if len(self.minheap) > len(self.maxheap):
return self.minheap.top() * 1.0
return (self.minheap.top() - self.maxheap.top()) / 2.0