數(shù)據(jù)流中的中位數(shù)

題目描述

如何得到一個數(shù)據(jù)流中的中位數(shù)?如果從數(shù)據(jù)流中讀出奇數(shù)個數(shù)值泞遗,那么中位數(shù)就是所有數(shù)值排序之后位于中間的數(shù)值殷蛇。如果從數(shù)據(jù)流中讀出偶數(shù)個數(shù)值,那么中位數(shù)就是所有數(shù)值排序之后中間兩個數(shù)的平均值戒幔。我們使用Insert()方法讀取數(shù)據(jù)流,使用GetMedian()方法獲取當前讀取數(shù)據(jù)的中位數(shù)土童。

思路

第一種思路诗茎,把全部元素存下來,排序献汗,取中位數(shù)敢订。如果數(shù)據(jù)量太大的情況下,效率較低罢吃。
第二種思路楚午,使用最大堆和最小堆來解決。
首先構(gòu)建一個最大堆和一個最小堆尿招,
隨后不斷接收數(shù)據(jù)流里的數(shù)據(jù)矾柜,每接收一個,將其插入到堆里面泊业。同時調(diào)整兩個堆里元素的數(shù)量把沼,保證兩個堆的數(shù)據(jù)差在一個之內(nèi)。
python里有內(nèi)置的heapq可以使用吁伺,但是這個heap是最小堆饮睬,所以還要創(chuàng)建一個最大堆。這里最大堆的創(chuàng)建方法在GitHub上學到了一個小技巧篮奄,把應(yīng)該加入最大堆的元素取相反數(shù)捆愁,然后加入到最小堆。那么這個裝滿相反數(shù)的最小堆就可以看成一個最大堆窟却。很巧妙的一個方法昼丑。

代碼

class Solution:
    def __init__(self):
        self.left = []
        self.right = []
    def Insert(self, num):
        from heapq import heappush, heappop
        #left 大堆 right 小堆
        if len(self.right) == 0 or num > self.right[0]:
            heappush(self.right, num)
        else:
            # push num的相反數(shù)進去,雖然left還是最小堆夸赫,但是里面的值都是相反數(shù)菩帝,反過來就是最大堆
            heappush(self.left, -num)
        # 不斷調(diào)整兩個堆,保證左右兩個堆里元素的數(shù)量平衡
        while len(self.left) - len(self.right) > 1:
            data = -heappop(self.left)
            heappush(self.right, data)
        while len(self.right) - len(self.left) > 1:
            data = heappop(self.right)
            heappush(self.left, -data)

    def GetMedian(self,xxx):
        if len(self.left) == len(self.right):
            if len(self.right) == 0:
                return 0
            min_heap = self.right[0]
            max_heap = -1*self.left[0]
            media = (min_heap+max_heap)/2.0
            return media
        elif len(self.left) > len(self.right):
            media = -1*self.left[0]
            return media
        else:
            return self.right[0]
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末茬腿,一起剝皮案震驚了整個濱河市呼奢,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌切平,老刑警劉巖握础,帶你破解...
    沈念sama閱讀 219,427評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異悴品,居然都是意外死亡禀综,警方通過查閱死者的電腦和手機简烘,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,551評論 3 395
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來定枷,“玉大人孤澎,你說我怎么就攤上這事∫琅福” “怎么了亥至?”我有些...
    開封第一講書人閱讀 165,747評論 0 356
  • 文/不壞的土叔 我叫張陵,是天一觀的道長贱迟。 經(jīng)常有香客問我姐扮,道長,這世上最難降的妖魔是什么衣吠? 我笑而不...
    開封第一講書人閱讀 58,939評論 1 295
  • 正文 為了忘掉前任茶敏,我火速辦了婚禮,結(jié)果婚禮上缚俏,老公的妹妹穿的比我還像新娘惊搏。我一直安慰自己,他們只是感情好忧换,可當我...
    茶點故事閱讀 67,955評論 6 392
  • 文/花漫 我一把揭開白布恬惯。 她就那樣靜靜地躺著,像睡著了一般亚茬。 火紅的嫁衣襯著肌膚如雪酪耳。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,737評論 1 305
  • 那天刹缝,我揣著相機與錄音碗暗,去河邊找鬼。 笑死梢夯,一個胖子當著我的面吹牛言疗,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播颂砸,決...
    沈念sama閱讀 40,448評論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼噪奄,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了人乓?” 一聲冷哼從身側(cè)響起梗醇,我...
    開封第一講書人閱讀 39,352評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎撒蟀,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體温鸽,經(jīng)...
    沈念sama閱讀 45,834評論 1 317
  • 正文 獨居荒郊野嶺守林人離奇死亡保屯,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,992評論 3 338
  • 正文 我和宋清朗相戀三年手负,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片姑尺。...
    茶點故事閱讀 40,133評論 1 351
  • 序言:一個原本活蹦亂跳的男人離奇死亡竟终,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出切蟋,到底是詐尸還是另有隱情统捶,我是刑警寧澤,帶...
    沈念sama閱讀 35,815評論 5 346
  • 正文 年R本政府宣布柄粹,位于F島的核電站喘鸟,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏驻右。R本人自食惡果不足惜什黑,卻給世界環(huán)境...
    茶點故事閱讀 41,477評論 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望堪夭。 院中可真熱鬧愕把,春花似錦、人聲如沸森爽。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,022評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽爬迟。三九已至橘蜜,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間雕旨,已是汗流浹背扮匠。 一陣腳步聲響...
    開封第一講書人閱讀 33,147評論 1 272
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留凡涩,地道東北人棒搜。 一個月前我還...
    沈念sama閱讀 48,398評論 3 373
  • 正文 我出身青樓,卻偏偏與公主長得像活箕,于是被迫代替她去往敵國和親力麸。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 45,077評論 2 355

推薦閱讀更多精彩內(nèi)容