zoukankan      html  css  js  c++  java
  • bnuoj 27411 数据结构维护区间RMQ

    很显然n方的复杂度过不了。

    于是考虑优化最值的查询,可以考虑用堆或者单调队列来做。

    堆:

     1 #include <iostream>
     2 #include <cstring>
     3 #include <cstdio>
     4 #include <queue>
     5 using namespace std;
     6 
     7 const int INF = 99999999;
     8 const int N = 32768;
     9 int a[N];
    10 int n, l, u;
    11 
    12 struct Node
    13 {
    14     int l;
    15     int s;
    16     Node () {}
    17     Node ( int _l, int _s )
    18     {
    19         l = _l;
    20         s = _s;
    21     }
    22     bool operator < ( const Node & t ) const
    23     {
    24         return s < t.s;
    25     }
    26 };
    27 
    28 int solve()
    29 {
    30     priority_queue<Node> q;
    31     int ans = INF;
    32     for ( int i = l; i <= n; i++ )
    33     {
    34         q.push( Node ( i - l, a[i - l] ) );
    35         while ( q.top().l + u < i ) q.pop();
    36         int tmp = a[i] - q.top().s;
    37         if ( tmp < ans ) ans = tmp;
    38     }
    39     return ans;
    40 }
    41 
    42 int main()
    43 {
    44     while ( scanf("%d", &n), n )
    45     {
    46         scanf("%d%d", &l, &u);
    47         a[0] = 0;
    48         for ( int i = 1; i <= n; i++ )
    49         {
    50             scanf("%d", a + i);
    51             a[i] += a[i - 1];
    52         }
    53         printf("%d
    ", solve());
    54     }
    55     return 0;
    56 }

    单调队列:

     1 #include <iostream>
     2 #include <cstring>
     3 #include <cstdio>
     4 #include <queue>
     5 using namespace std;
     6 
     7 const int INF = 99999999;
     8 const int N = 32768;
     9 int a[N];
    10 int n, l, u;
    11 int head, tail;
    12 
    13 struct Node
    14 {
    15     int l, s;
    16 } q[N];
    17 
    18 int solve()
    19 {
    20     int ans = INF;
    21     head = tail = 0;
    22     for ( int i = l; i <= n; i++ )
    23     {
    24         while ( head < tail && a[i - l] > q[tail - 1].s )
    25         {
    26             tail--;
    27         }
    28         q[tail].l = i - l, q[tail].s = a[i - l];
    29         tail++;
    30         while ( q[head].l + u < i ) head++;
    31         int tmp = a[i] - q[head].s;
    32         if ( tmp < ans ) ans = tmp;
    33     }
    34     return ans;
    35 }
    36 
    37 int main()
    38 {
    39     while ( scanf("%d", &n), n )
    40     {
    41         scanf("%d%d", &l, &u);
    42         a[0] = 0;
    43         for ( int i = 1; i <= n; i++ )
    44         {
    45             scanf("%d", a + i);
    46             a[i] += a[i - 1];
    47         }
    48         printf("%d
    ", solve());
    49     }
    50     return 0;
    51 }

     块状链表:

      1 #include <iostream>
      2 #include <cstring>
      3 #include <cstdio>
      4 #include <cmath>
      5 using namespace std;
      6 
      7 const int INF = 999999999;
      8 const int N = 32768;
      9 const int M = 500;
     10 int a[N];
     11 int n, tot;
     12 int ps;
     13 int lower, upper;
     14 
     15 int max( int a, int b )
     16 {
     17     return a > b ? a : b;
     18 }
     19 
     20 int min( int a, int b )
     21 {
     22     return a < b ? a : b;
     23 }
     24 
     25 struct Block
     26 {
     27     int num[M];
     28     int size, maxn;
     29     void init()
     30     {
     31         size = 0;
     32         maxn = -INF;
     33     }
     34     void push( int tmp )
     35     {
     36         num[size++] = tmp;
     37         if ( tmp > maxn ) maxn = tmp;
     38     }
     39 } bl[M];
     40 
     41 int query( int l, int r )
     42 {
     43     l++, r++;
     44     int cur = 0, ncur = 0;
     45     while ( l > ps )
     46     {
     47         l -= ps;
     48         cur++;
     49     }
     50     while ( r > ps )
     51     {
     52         r -= ps;
     53         ncur++;
     54     }
     55     int ans = -INF;
     56     for ( int i = cur + 1; i <= ncur - 1; i++ )
     57     {
     58         ans = max( ans, bl[i].maxn );
     59     }
     60     if ( cur == ncur )
     61     {
     62         for ( int j = l - 1; j < r; j++ )
     63         {
     64             ans = max( ans, bl[cur].num[j] );
     65         }
     66     }
     67     else
     68     {
     69         for ( int j = l - 1; j < bl[cur].size; j++ )
     70         {
     71             ans = max( ans, bl[cur].num[j] );
     72         }
     73         for ( int j = 0; j < r; j++ )
     74         {
     75             ans = max( ans, bl[ncur].num[j] );
     76         }
     77     }
     78     return ans;
     79 }
     80 
     81 int main()
     82 {
     83     while ( scanf("%d", &n), n )
     84     {
     85         scanf("%d%d", &lower, &upper);
     86         a[0] = 0;
     87         for ( int i = 1; i <= n; i++ )
     88         {
     89             scanf("%d", a + i);
     90             a[i] += a[i - 1];
     91         }
     92         tot = 0;
     93         bl[tot].init();
     94         ps = sqrt((double)n);
     95         for ( int i = 0; i <= n; i++ )
     96         {
     97             if ( bl[tot].size == ps )
     98             {
     99                 tot++;
    100                 bl[tot].init();
    101             }
    102             bl[tot].push(a[i]);
    103         }
    104         int ans = INF;
    105         for ( int i = lower; i <= n; i++ )
    106         {
    107             int qq = query( max( i - upper, 0 ), i - lower );
    108             ans = min( ans, a[i] - qq );
    109         }
    110         printf("%d
    ", ans);
    111     }
    112     return 0;
    113 }

    还可以用线段树或者RMQ的ST算法,解法实在是太多了。

  • 相关阅读:
    word2vec
    视频推荐系统
    python基础
    go-elasticsearch
    Docker 部署 go项目
    gohbase
    禅道部署linux
    jmeter 报错 Error occurred during initialization of VM Could not reserve enough space for object heap
    jarvis OJ-DSA
    算法-我的第一本算法书(一)
  • 原文地址:https://www.cnblogs.com/huoxiayu/p/4470981.html
Copyright © 2011-2022 走看看