剑指 Offer 41. 数据流中的中位数

62 篇文章 1 订阅
39 篇文章 0 订阅
该博客主要介绍了如何利用大顶堆和小顶堆来实现实时计算数据流中的中位数。通过维护两个堆,一个大顶堆保存较小的一半数据,一个小顶堆保存较大的一半数据,确保两者数量的平衡,从而快速获取中位数。在添加新元素时,根据堆的大小调整元素的归属,并在需要时进行堆之间的元素迁移。代码中展示了MedianFinder类的实现,包括addNum方法用于添加新数和findMedian方法用于获取当前中位数。
摘要由CSDN通过智能技术生成

剑指 Offer 41. 数据流中的中位数

链接

剑指 Offer 41. 数据流中的中位数

思路

用大顶堆+小顶堆方法,可以看作大顶堆是普通班,小顶堆是实验班。数量上时刻保持 小顶-大顶<=1(两堆相等或者小顶比大顶多一个)。新学生先入普通班(大顶堆),此时可能会失去平衡了,于是取大顶堆的第一个(班里最好的学生)加入实验班(小顶堆),判断若数量过多(不是等于或多一个),取第一个(实验班里最差的学生)到普通班(大顶堆)里。取中位数的时候,若两堆数量相等,则各取堆顶取平均,若小顶比大顶多一,则多的那一个就是中位数

代码

public class MedianFinder
{
    Queue<Integer> A, B;

    //用 PriorityQueue<> 建堆
    public MedianFinder()
    {
        //A 存放(N / 2)--> N 为偶数 或 (N + 1) --> N为奇数
        A = new PriorityQueue<>();  //小顶堆:保存较大的一半
        //B 存放(N、 2)--> N 为偶数 或 (N - 1) --> N 为奇数
        B = new PriorityQueue<>((x, y) -> (y - x)); //大顶堆:保存较小的一半
    }

    public void addNum(int num)
    {
        if (A.size() != B.size())
        {
            A.add(num);
            B.add(A.poll());
        } else
        {
            //长度相等
            B.add(num);
            A.add(B.poll());
        }
    }

    public double findMedian()
    {
        return A.size() != B.size() ? A.peek() : (A.peek() + B.peek()) / 2.0;
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

枳洛淮南✘

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值