难度困难
中位数是有序序列最中间的那个数。如果序列的长度是偶数,则没有最中间的数;此时中位数是最中间的两个数的平均数。
例如:
[2,3,4]
,中位数是3
[2,3]
,中位数是(2 + 3) / 2 = 2.5
给你一个数组 nums,有一个长度为 k 的窗口从最左端滑动到最右端。窗口中有 k 个数,每次窗口向右移动 1 位。你的任务是找出每次窗口移动后得到的新窗口中元素的中位数,并输出由它们组成的数组。
示例:
给出 nums = [1,3,-1,-3,5,3,6,7]
,以及 k = 3。
窗口位置 中位数 --------------- ----- [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
因此,返回该滑动窗口的中位数数组 [1,-1,-1,3,5,6]
。
class Solution { public: vector<double> medianSlidingWindow(vector<int>& nums, int k) { vector<double> res; for(int i = 0; i <= nums.size()-k;i++) { vector<long> temp(nums.begin()+i,nums.begin()+i+k); //开区间 sort(temp.begin(),temp.end()); double a = k%2!=0?temp[k/2]: double(temp[k/2]+temp[k/2-1])/2.0; res.emplace_back(a); } return res; } };
class Solution { public: vector<double> medianSlidingWindow(vector<int>& nums, int k) { vector<double> ret; multiset<int> window(nums.begin(), nums.begin() + k); // 初始化set,将前k个数存入set auto mid = std::next(window.begin(), k / 2); // 基数:获取中数的位置,偶数:获取中数计数参数的后一个数的位置 for (int idx = k;idx < nums.size() ; idx++) { // 1、计数每组窗口中数组的中数,并存入ret中 auto midValue = ((double)(*mid) + (double)*next(mid, k % 2 - 1)) / 2; ret.push_back(midValue); // 遍历完了,退出 if (idx == nums.size()) { break; } // 窗口后移 window.insert(nums[idx]); if (nums[idx] < *mid) mid--; // same as mid = prev(mid) // Remove outgoing element if (nums[idx - k] <= *mid) mid++; // same as mid = next(mid) // 删除一个元素 window.erase(window.lower_bound(nums[idx-k])); } return ret; } };
标签:窗口,idx,nums,mid,中位数,vector,滑动,480 From: https://www.cnblogs.com/zle1992/p/16614542.html