SubsequenceTime Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 3996 Accepted Submission(s): 1309
Problem Description
There is a sequence of integers. Your task is to find the longest subsequence that satisfies the following condition: the difference between the maximum element and the minimum element of the subsequence is no smaller than m and no larger than k.
Input
There are multiple test cases.
For each test case, the first line has three integers, n, m and k. n is the length of the sequence and is in the range [1, 100000]. m and k are in the range [0, 1000000]. The second line has n integers, which are all in the range [0, 1000000]. Proceed to the end of file.
Output
For each test case, print the length of the subsequence on a single line.
Sample Input
Sample Output
Source
Recommend
|
题意:求一个最长子序列,序列最大值与最小值的差d, m<=d<=k。
思路:用两个单调队列维护最大值、最小值,从左往右扫一遍。当队首元素差大于k,删除队首元素,我们需要删除的应该是两个队首元素数组下标小的那个。我们这样考虑,假设当前扫到i,答案ans=max(ans,i-max(que1[head1].index,que2[head2].index)+1),如果我们删除下标大的那个队首元素,那么对应的队列必然要head++,即满足条件的下标在变大,那么max(que1[head1].index,que2[head2].index)必然也跟着增大,不能满足max(que1[head1].index,que2[head2].index)尽可能小,而删除下标小的队首元素,可以在max(que1[head1].index,que2[head2].index)尽可能小的情况下满足m<=d<=k。详见程序:
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int MAXN=100000+100;
int n,m,k;
int head1,tail1,head2,tail2;
int a[MAXN];
struct node
{
int val,index;
}que1[MAXN],que2[MAXN];
int main()
{
//freopen("text.txt","r",stdin);
while(~scanf("%d%d%d",&n,&m,&k))
{
for(int i=1;i<=n;i++)
scanf("%d",&a[i]);
int ans=0,last1=0,last2=0;
head1=tail1=head2=tail2=0;
for(int i=1;i<=n;i++)
{
while(head1<tail1 && que1[tail1-1].val>a[i]) tail1--;
que1[tail1].val=a[i]; que1[tail1++].index=i;
while(head2<tail2 && que2[tail2-1].val<a[i]) tail2--;
que2[tail2].val=a[i]; que2[tail2++].index=i;
while(que2[head2].val-que1[head1].val>k)
{
if(que2[head2].index<que1[head1].index)
last2=que2[head2++].index;
else
last1=que1[head1++].index;
}
if(que2[head2].val-que1[head1].val>=m)
ans=max(ans,i-max(last1,last2));
}
printf("%d\n",ans);
}
return 0;
}