leetcode 239. 滑动窗口最大值

一:暴力解法,能ac但是时间复杂度O(nk)

class Solution {
public:
    vector<int> maxSlidingWindow(vector<int>& nums, int k) {
        int len=nums.size();
        if(len==0) return {};
        vector<int> res;
        for(int i=0;i<=len-k;i++){
            int key=nums[i];
            for(int j=1;j<k;j++){
                if(key<nums[i+j]) key=nums[i+j];
            }
            res.push_back(key);
        }
        return res;
    }
};

 

二,维护一个特殊的优先队列(使用deque实现)假设当前队列已经是优先队列(最大值在队首),而且这个队列是有序递减的,那么当新加入一个元素时执行两个操作,

1)检查队首下标是否合法,假如队首下标已经不在滑窗内,则将其弹出;

2)检查已有的队列中的元素是否比当前元素小,小的元素全部弹出。由于已经是按值有序递减的数列,那么只需要不断的比较末尾和当前元素,即可完成该项;

此时已经对新进入的元素维护好了一个最大元素下标在队首,元素下标按值有效递减,且下标从左到右是有序的的一个队列;获取队首元素可得当前滑窗的大小;

class Solution {
public:
    vector<int> maxSlidingWindow(vector<int>& nums, int k) {
        if(nums.size()<k || k<=0) return {};
        vector<int> res;
        deque<int> dq;
        int len=nums.size();
        for(int i=0;i<len;i++){
            if(!dq.empty() && dq.front()==i-k)
                dq.pop_front();
            while(!dq.empty() && nums[dq.back()]<nums[i]){
                dq.pop_back();
            }
            dq.push_back(i);//当前的有效下降子序列已经维护好;
            if(i>=k-1){
                res.push_back(nums[dq.front()]);
            }
        }
        return res;
    }
};

 

posted @ 2019-04-10 20:14  Joel_Wang  阅读(235)  评论(0编辑  收藏  举报