单调队列进阶

来源:互联网 发布:用u盘安装linux 编辑:程序博客网 时间:2024/06/06 08:38

题目地址 http://acm.hdu.edu.cn/showproblem.php?pid=3530

题目大意: 给定一个数列,长度n(1<=n<=100000), 值m和k, 求最长子序列,满足当中的最大值-最小值差不小于m且不大于k。

与前面介绍的题目不太一样,这道题反过来了,没有规定窗长度,相反是要我们求要求条件的最大的窗。

道理还是一样,当窗长规定为l时,我们只需要保存i的前l-1个数当中的最大值和最小值,而要我们求窗长时,我们可以自己设定窗的开始位置start,同样保存从位置start到到当前i的这段数中的最大值单调队列和最小值单调队列。

假设queMax是最递减队列,queMin是递增队列,分别保存的是从start到i这段长为i-start+1的数的最大值和最小值,headMax, headMin 是他们队列的头索引。如果m<=queMax[headMax]-queMin[headMin]<=k,那这段长为i-k+1的序列就满足题目的要求。

假设我们start到i的序列满足要求,我们接下来当然是看加上第i+1个数后是否还满足要求。方法如下:

1.将第i+1个数插入到两个队列当中,然后看是否满足要求,如果满足要求,保存长度(i+1)-k+1。

2.否则,如果queMax[headMax]-queMin[headMin]<=m,不作任何处理;

           如果queMax[headMax]-queMin[headMin]>=k,那么我们就要增加headMin或headMax,为了求最长序列,我们当然先择下标最小的那个头元素了。一直将headMin或headMax增加到满足条件。

 

原创粉丝点击