deque
/*
What we should do next is to shrink left pointer because of limit.
If current.max - current.min > limit.
we need to dequeue the "tail" element who is smaller than the nums[right].
Since, those "old small tail" elements will never be the range maximum from now on.
After "clean up" the "old small tail" elements, add nums[right] into the deque,
and then, the head of deque is the current maximum.
Time O(N)
Space O(N)
*/
class Solution {
public int longestSubarray(int[] A, int limit) {
Deque<Integer> maxd = new ArrayDeque<>();
Deque<Integer> mind = new ArrayDeque<>();
int i = 0, res = 0;
for (int j = 0; j < A.length; ++j) {
while (!maxd.isEmpty() && A[j] > maxd.peekLast()) maxd.pollLast();
maxd.add(A[j]);
while (!mind.isEmpty() && A[j] < mind.peekLast()) mind.pollLast();
mind.add(A[j]);
if (maxd.peek() - mind.peek() > limit) {
if (maxd.peek() == A[i]) maxd.poll();
if (mind.peek() == A[i]) mind.poll();
i++;
}
res = Math.max(res, j - i + 1);
}
return res;
}
}