-
Notifications
You must be signed in to change notification settings - Fork 21
/
295. Find Median from Data Stream.java
executable file
·77 lines (65 loc) · 2.3 KB
/
295. Find Median from Data Stream.java
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
H
tags: Heap, Design, MinHeap, MaxHeap
time: O(1) get, O(logn) addNum
space: O(n)
#### MaxHeap/MinHeap
- 把Input stream想成向上的山坡. 山坡中间那点,自然就是median.
- 前半段,作为maxHeap,关注点是PriorityQueue的峰点,也就是实际上的median.
- 后半段,作为minHeap,正常的PriorityQueue。 开头是最小的。
#### 注意
- 这里要首先定好, 哪一个queue是多存一个element的. 这里选maxHeap: maxHeap.size() == minHeap.size() + 1 || minHeap.size()
- 必须先维护maxHeap里面有个元素, 否则null了会在比较大小时出问题.
```
/*
Median is the middle value in an ordered integer list. If the size of the list is even, there is no middle value. So the median is the mean of the two middle value.
Examples:
[2,3,4] , the median is 3
[2,3], the median is (2 + 3) / 2 = 2.5
Design a data structure that supports the following two operations:
void addNum(int num) - Add a integer number from the data stream to the data structure.
double findMedian() - Return the median of all elements so far.
For example:
addNum(1)
addNum(2)
findMedian() -> 1.5
addNum(3)
findMedian() -> 2
*/
/*
- use maxHeap, minHeap.
- normalize the heap size
- always fix maxHeah with the additional item
- calc: if size of 2 heaps are the same, do average.
*/
class MedianFinder {
PriorityQueue<Integer> maxHeap, minHeap;
/** initialize your data structure here. */
public MedianFinder() {
minHeap = new PriorityQueue<>();
maxHeap = new PriorityQueue<>(Comparator.reverseOrder());
}
public void addNum(int num) {
if (maxHeap.isEmpty()) maxHeap.offer(num);
else if (num <= maxHeap.peek()) maxHeap.offer(num);
else minHeap.offer(num);
// adjust:
if (maxHeap.size() > minHeap.size() + 1) {
minHeap.offer(maxHeap.poll());
} else if (minHeap.size() > maxHeap.size()) {
maxHeap.offer(minHeap.poll());
}
}
public double findMedian() {
if (maxHeap.size() == minHeap.size()) {
return (maxHeap.peek() + minHeap.peek()) / 2.0;
}
return maxHeap.peek();
}
}
/**
* Your MedianFinder object will be instantiated and called as such:
* MedianFinder obj = new MedianFinder();
* obj.addNum(num);
* double param_2 = obj.findMedian();
*/
```