zoukankan      html  css  js  c++  java
  • hdu 3530 Subsequence 单调队列

    题目链接

    题目给出n个数, 一个下界m, 一个上界k, 让你求出最长的一段序列, 满足这段序列中的最大的数-最小的数<=k&&>=m, 输出这段长度。

    可以维护两个队列, 一个队列的队头元素是这一段中的最大值,是一个单调递减的数列; 另一个队列是这段中的最小值, 单调递增的数列。具体看代码。

     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 const int maxn = 1e5+5;
     4 int a[maxn], q1[maxn], q2[maxn];
     5 int main()
     6 {
     7     int n, m, k;
     8     while(cin>>n>>m>>k) {
     9         for(int i = 0; i<n; i++) {
    10             scanf("%d", &a[i]);
    11         }
    12         int st1 = 0, st2 = 0, ed1 = 0, ed2 = 0, ans = 0, now = 0;
    13         for(int i = 0; i<n; i++) {
    14             while(st1<ed1&&a[q1[ed1-1]]<a[i])       //q1维护一个单调递减的数列,这样队头元素是最大值, 第二个是第二大的值
    15                 ed1--;
    16             while(st2<ed2&&a[q2[ed2-1]]>a[i])       //q2维护一个单调递增的数列, 队头是最小值。
    17                 ed2--;
    18             q1[ed1++] = q2[ed2++] = i;              
    19             while(st1<ed1&&st2<ed2&&a[q1[st1]]-a[q2[st2]]>k) {      //如果最大值-最小值大于k
    20                 if(q1[st1]<q2[st2]) {
    21                     now = q1[st1++]+1;                 //如果最大值在序列中的位置小于最小值
    22                 } else {
    23                     now = q2[st2++]+1;
    24                 }
    25             }
    26             if(st1<ed1&&st2<ed2&&a[q1[st1]]-a[q2[st2]]>=m) {
    27                 ans = max(ans, i-now+1);                //只有最大值-最小值大于等于m的时候才更新ans
    28             }
    29         }
    30         cout<<ans<<endl;
    31     }
    32 }
  • 相关阅读:
    Servlet介绍(一)
    iOS Dev (50)用代码实现图片加圆角
    Codeforces Round #265 (Div. 2) D. Restore Cube 立方体推断
    JVM:垃圾回收机制和调优手段
    Memcachedclient-XMemcached使用
    JVM中类的卸载机制
    血型统计
    iOS 事件传递及响应过程
    java 对象参数去空格方式
    spring aop 一个挡板例子
  • 原文地址:https://www.cnblogs.com/yohaha/p/5040897.html
Copyright © 2011-2022 走看看