leetcode刷題筆記295題 資料流的中位數
阿新 • • 發佈:2020-11-19
leetcode刷題筆記295題 資料流的中位數
源地址:295. 資料流的中位數
問題描述:
中位數是有序列表中間的數。如果列表長度是偶數,中位數則是中間兩個數的平均值。
例如,
[2,3,4] 的中位數是 3
[2,3] 的中位數是 (2 + 3) / 2 = 2.5
設計一個支援以下兩種操作的資料結構:
void addNum(int num) - 從資料流中新增一個整數到資料結構中。
double findMedian() - 返回目前所有元素的中位數。
示例:addNum(1)
addNum(2)
findMedian() -> 1.5
addNum(3)
findMedian() -> 2
進階:如果資料流中所有整數都在 0 到 100 範圍內,你將如何優化你的演算法?
如果資料流中 99% 的整數都在 0 到 100 範圍內,你將如何優化你的演算法?
//使用自大到小的優先佇列down模擬大頂堆,使用自小到大的優先佇列up模擬小頂堆,二者結合構成對頂堆 //保證down.size = up.size || up.size+1 //中位數即為down的top位置計算或up和down的top位置計算 import scala.collection.mutable.PriorityQueue class MedianFinder() { /** initialize your data structure here. */ val up = PriorityQueue.empty[Int](Ordering.by(n => n)).reverse val down = PriorityQueue.empty[Int](Ordering.by(n => n)) def addNum(num: Int) { if (down.isEmpty == true || num <= down.head){ down.enqueue(num) if (down.size > up.size + 1){ up.enqueue(down.head) down.dequeue() } } else { up.enqueue(num) if (up.size > down.size){ down.enqueue(up.head) up.dequeue() } } } def findMedian(): Double = { if ((up.size + down.size) % 2 == 1) return down.head else return (up.head + down.head)/2.0 } } /** * Your MedianFinder object will be instantiated and called as such: * var obj = new MedianFinder() * obj.addNum(num) * var param_2 = obj.findMedian() */