862. 和至少为 K 的最短子数组
看题目是与和有关的问题,那么就联想到前缀和,先把数组的前缀和算出来,在队列里插入下标,当当前前缀和减去队首前缀和满足条件时,说明有满足条件的数组出现,计算元素个数,同时把队首弹出,直到不满足条件,为了维护队列单调递增,当当前前缀和小于队尾前缀和,即将队尾弹出,直到符合递增队列。
为什么维护单调递增队列,因为要求和至少为k的子数组,队首存放最小的下标,与最小值的差值是最大的,更可能满足条件。
class Solution {
public:
int shortestSubarray(vector<int>& nums, int k) {
int n=nums.size();
vector<long long> sum(n+1,0);
for(int i=0;i<n;i++)
sum[i+1]=sum[i]+nums[i];
int ans=INT_MAX;
deque<int> que;
for(int i=0;i<sum.size();i++)
{
while(!que.empty()&&sum[i]-sum[que.front()]>=k)
{
ans=min(ans,i-que.front());
que.pop_front();
}
while(!que.empty()&&sum[i]<=sum[que.back()])
que.pop_back();
que.push_back(i);
}
if(ans==INT_MAX)
return -1;
else
return ans;
}
};