239. Sliding Window Maximum
2016-06-28 22:25
169 查看
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.
For example,
Given nums =
3.
Therefore, return the max sliding window as
Note:
You may assume k is always valid, ie: 1 ≤ k ≤ input array's size for non-empty array.
Follow up:
Could you solve it in linear time?
Hint:
How about using a data structure such as deque (double-ended queue)?
The queue size need not be the same as the window’s size.
Remove redundant elements and the queue should store only elements that need to be considered.
使用有序的Treemap将元素值和其次数做映射,扫描移动,每小段的max值即为Treemap中的lastkey。
时间复杂度O(NlogN)
-------------------------------------------------------------------------------------------
另外好的方法,摘自 https://leetcode.com/discuss/46578/java-o-n-solution-using-deque-with-explanation
We scan the array from 0 to n-1, keep "promising" elements in the deque. The algorithm is amortized O(n) as each element is put and polled once.
At each i, we keep "promising" elements, which are potentially max number in window [i-(k-1),i] or any subsequent window. This means
If an element in the deque and it is out of i-(k-1), we discard them. We just need to poll from the head, as we are using a deque and elements are ordered as the sequence in the array
Now only those elements within [i-(k-1),i] are in the deque. We then discard elements smaller than a[i] from the tail. This is because if a[x] <a[i] and x<i, then a[x] has no chance to be the "max" in [i-(k-1),i],
or any other subsequent window: a[i] would always be a better candidate.
As a result elements in the deque are ordered in both sequence in array and their value. At each step the head of the deque is the max element in [i-(k-1),i]
window moves right by one position.
For example,
Given nums =
[1,3,-1,-3,5,3,6,7], and k =
3.
Window position Max --------------- ----- [1 3 -1] -3 5 3 6 7 3 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 5 1 3 -1 -3 [5 3 6] 7 6 1 3 -1 -3 5 [3 6 7] 7
Therefore, return the max sliding window as
[3,3,5,5,6,7].
Note:
You may assume k is always valid, ie: 1 ≤ k ≤ input array's size for non-empty array.
Follow up:
Could you solve it in linear time?
Hint:
How about using a data structure such as deque (double-ended queue)?
The queue size need not be the same as the window’s size.
Remove redundant elements and the queue should store only elements that need to be considered.
使用有序的Treemap将元素值和其次数做映射,扫描移动,每小段的max值即为Treemap中的lastkey。
时间复杂度O(NlogN)
public static int[] maxSlidingWindow(int[] nums, int k) { int len=nums.length; if(len<1) return new int[]{}; TreeMap<Integer, Integer> treemap=new TreeMap<>(); int cnt=0; int[] retarr=new int[len-k+1]; for(int i=0;i<k;i++) if(!treemap.containsKey(nums[i])) treemap.put(nums[i], 1); else { treemap.put(nums[i], treemap.get(nums[i])+1); } retarr[cnt++]=treemap.lastKey(); for(int i=1;i<=len-k;i++) { int removeele=nums[i-1]; int times=treemap.get(removeele); if(times==1) treemap.remove(removeele); else { treemap.put(removeele,times-1); } if(!treemap.containsKey(nums[i+k-1])) treemap.put(nums[i+k-1], 1); else { treemap.put(nums[i+k-1], treemap.get(nums[i+k-1])+1); } retarr[cnt++]=treemap.lastKey(); } return retarr; }
-------------------------------------------------------------------------------------------
另外好的方法,摘自 https://leetcode.com/discuss/46578/java-o-n-solution-using-deque-with-explanation
Java O(n) solution using deque with explanation
We scan the array from 0 to n-1, keep "promising" elements in the deque. The algorithm is amortized O(n) as each element is put and polled once.At each i, we keep "promising" elements, which are potentially max number in window [i-(k-1),i] or any subsequent window. This means
If an element in the deque and it is out of i-(k-1), we discard them. We just need to poll from the head, as we are using a deque and elements are ordered as the sequence in the array
Now only those elements within [i-(k-1),i] are in the deque. We then discard elements smaller than a[i] from the tail. This is because if a[x] <a[i] and x<i, then a[x] has no chance to be the "max" in [i-(k-1),i],
or any other subsequent window: a[i] would always be a better candidate.
As a result elements in the deque are ordered in both sequence in array and their value. At each step the head of the deque is the max element in [i-(k-1),i]
public int[] maxSlidingWindow(int[] a, int k) { if (a == null || k <= 0) { return new int[0]; } int n = a.length; int[] ret = new int[n-k+1]; int cnt = 0; // store index ArrayDeque<Integer> q = new ArrayDeque<>(); for (int i = 0; i < a.length; i++) { // remove numbers out of range k while (!q.isEmpty() && q.peek() < i - k + 1) { q.poll(); } // remove smaller numbers in k range as they are useless while (!q.isEmpty() && a[q.peekLast()] < a[i]) { q.pollLast(); } // q contains index... r contains content q.offer(i); if (i >= k - 1) { ret[cnt++] = a[q.peek()]; } } return ret; }
相关文章推荐
- 016-kruskal算法-贪心-《算法设计技巧与分析》M.H.A学习笔记
- 达达的mysql数据库优化之路
- java之远程接口调用
- Java基础与案例开发详解の抽象和封装
- (OK)(OK) using adb with a NAT'ed VM - VirtualBox - NAT Port Forwarding
- Hibernate(四)
- pthread_mutex_t 和 pthread_cond_t 配合使用的简要分析
- C++函数参数中的: 值传递,地址传递,双向传递
- servlet 和filter区别和servlet、filter、interceptor的执行顺序
- hadoop1.2.1伪分布式安装
- pl/sql %TYPE
- 【hdu】2369 Bone Collector II【kth背包】
- c++15、流&输入输出流入栈方式
- 布局管理-分割窗口类QSplitter类
- [LeetCode] Largest Divisible Subset 最大可整除的子集合
- 使用ImageLoader实现图片异步加载
- 《An Introduction to Signal Smoothing》译文
- AJAX POST 到特定链接,一直提示400错误,但是单独在浏览器里面又可以打开这个链接!
- 禁止UITextField 使用粘贴复制功能
- 《An Introduction to Signal Smoothing》译文