Find Median from Data Stream

题目:

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:

add(1)
add(2)
findMedian() -> 1.5
add(3) 
findMedian() -> 2


思路: 刚开始想的做法是
1、插入排序,维护有序数据。 插入复杂度太高。
2、第二个想法: 利用第k大算法,用了C++的nth_element, 超时
3、最终的想法: 维护两个堆, 一个最大堆, 一个最小堆。 两个size保持相同(数目最大差别不能超过1), 最大堆的元素都不大于最小堆的元素。 这样插入,查找的复杂度都是 O(log n)
另外C++ 最小堆的是这样声明的, priority_queue<int, vector<int>, greater<int> >q_min;

AC代码:


class MedianFinder
{
public:

    priority_queue<int, vector<int>, greater<int> >q_min;
    priority_queue<int>q_max;
    void addNum(int num)
    {
        if(q_max.size() == 0) q_max.push(num);
        else if( num <= q_max.top() ) q_max.push(num);
        else q_min.push(num);
        while(q_max.size() > q_min.size() + 1)
        {
            q_min.push(q_max.top());
            q_max.pop();
        }
        while(q_max.size() < q_min.size())
        {
            q_max.push(q_min.top());
            q_min.pop();
        }
    }

    double findMedian()
    {
        if(q_min.size() == q_max.size())
        {
            return (q_min.top() + q_max.top())/2.0;
        }
        else
        {
            return q_max.top()*1.0;
        }
    }
};

 



posted @ 2016-04-24 14:55  Gu Feiyang  阅读(127)  评论(0)    收藏  举报