zoukankan      html  css  js  c++  java
  • [LeetCode] 480. Sliding Window Median

    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

    Given an array nums, there is a sliding window of size k which is moving from the very left of the array to the very right. You can only see the k numbers in the window. Each time the sliding window moves right by one position. Your job is to output the median array for each window in the original array.

    For example,
    Given nums = [1,3,-1,-3,5,3,6,7], and k = 3.

    Window position                Median
    ---------------               -----
    [1  3  -1] -3  5  3  6  7       1
     1 [3  -1  -3] 5  3  6  7       -1
     1  3 [-1  -3  5] 3  6  7       -1
     1  3  -1 [-3  5  3] 6  7       3
     1  3  -1  -3 [5  3  6] 7       5
     1  3  -1  -3  5 [3  6  7]      6
    

    Therefore, return the median sliding window as [1,-1,-1,3,5,6].

    Note:
    You may assume k is always valid, ie: k is always smaller than input array's size for non-empty array.
    Answers within 10^-5 of the actual value will be accepted as correct.

    滑动窗口中位数。题目就是题意。这个题的思路跟295题非常像,也是需要用到优先队列。

    首先创建一个长度为i - k + 1的数组记录结果,一个最大堆,一个最小堆。之后开始遍历input,按照295题的思路决定到底是把当前的数字加入最大堆还是最小堆。原则上还是保证两个堆一样大或者最大堆多一个元素

    • 如果最小堆size较大或者两者size一样,则将当前数字放入最大堆
    • 如果最大堆size较大,则将当前数字放入最小堆

    之后判断如果两个堆中存放的元素个数达到K了,此时就可以开始结算了。注意结算最后记得移除sliding window的第一个元素,因为window会往右移动。

    时间O(nlogk)

    空间O(n)

    Java实现

     1 class Solution {
     2     public double[] medianSlidingWindow(int[] nums, int k) {
     3         double[] res = new double[nums.length - k + 1];
     4         PriorityQueue<Integer> left = new PriorityQueue<>(Collections.reverseOrder());
     5         PriorityQueue<Integer> right = new PriorityQueue<>();
     6         for (int i = 0; i < nums.length; i++) {
     7             if (left.size() <= right.size()) {
     8                 right.add(nums[i]);
     9                 left.add(right.remove());
    10             } else {
    11                 left.add(nums[i]);
    12                 right.add(left.remove());
    13             }
    14             if (left.size() + right.size() == k) {
    15                 double median;
    16                 if (left.size() == right.size()) {
    17                     median = (double) ((long) left.peek() + (long) right.peek()) / 2;
    18                 } else {
    19                     median = (double) left.peek();
    20                 }
    21                 int start = i - k + 1;
    22                 res[start] = median;
    23                 if (!left.remove(nums[start])) {
    24                     right.remove(nums[start]);
    25                 }
    26             }
    27         }
    28         return res;
    29     }
    30 }

    相关题目

    295. Find Median from Data Stream

    480. Sliding Window Median

    LeetCode 题目总结

  • 相关阅读:
    访问的站点提示输入用户名密码
    ASP.NET Session 过期问题
    c#和VB代码转化网址
    整理 css 小技巧
    asp.net当修改header时提示:The Controls collection cannot be modified because the control contains code blocks (i.e. <% ... %>)
    sql server 2005 replication 设置
    动态加载CSS和Javascript文件 javascript 和asp.net.
    一台机子上安装两个版本的mysql
    sql删除所有表外键和表
    Griview中的删除按钮添加“确认提示”
  • 原文地址:https://www.cnblogs.com/cnoodle/p/13063517.html
Copyright © 2011-2022 走看看