• hdu 5349 维护序列 OR Treap


    由于只删除最小值和只查询最大值,所以我们只要维护一个maxn和一个size即可,需要注意的是删除到集合空时需要重新将maxn赋值为无穷小。

     1 #include <iostream>
     2 #include <cstring>
     3 #include <cstdio>
     4 using namespace std;
     5 
     6 int main ()
     7 {
     8     int n;
     9     while ( scanf("%d", &n) != EOF )
    10     {
    11         int op, tmp, maxn = -1111111111, size = 0;
    12         for ( int i = 0; i < n; i++ )
    13         {
    14             scanf("%d", &op);
    15             if ( op == 1 )
    16             {
    17                 scanf("%d", &tmp);
    18                 size++;
    19                 if ( tmp > maxn ) maxn = tmp; 
    20             }
    21             else if ( op == 2 )
    22             {
    23                 if ( size > 0 )
    24                 {
    25                     size--;
    26                     if ( size == 0 ) maxn = -1111111111;
    27                 }               
    28             }
    29             else
    30             {
    31                 if ( size == 0 )
    32                 {
    33                     printf("0
    ");
    34                 }
    35                 else
    36                 {
    37                     printf("%d
    ", maxn);    
    38                 }
    39             }
    40         }
    41     }
    42     return 0;
    43 }

    另外,别的平衡的数据结构也可以过,这里用的是Treap(主要是测模板),比赛推荐用multiset。

      1 #include <iostream>
      2 #include <cstring>
      3 #include <cstdlib>
      4 #include <cstdio>
      5 using namespace std;
      6 
      7 struct Node 
      8 {
      9     Node * ch[2];
     10     int v, r, size;
     11     int cmp( int x )
     12     {
     13         if ( x == v ) return -1;
     14         return x < v ? 0 : 1;
     15     }    
     16     void maintain()
     17     {
     18         size = 1;
     19         if ( ch[0] != NULL ) size += ch[0]->size;
     20         if ( ch[1] != NULL ) size += ch[1]->size;
     21     }
     22 };
     23 
     24 Node * root;
     25 
     26 void rotate( Node * & o, int d )
     27 {
     28     Node * k = o->ch[d ^ 1];
     29     o->ch[d ^ 1] = k->ch[d];
     30     k->ch[d] = o;
     31     o->maintain();
     32     k->maintain();
     33     o = k;
     34 }
     35 
     36 void insert( Node * & o, int x )
     37 {
     38     if ( o == NULL )
     39     {
     40         o = new Node();
     41         o->ch[0] = o->ch[1] = NULL;
     42         o->v = x;
     43         o->r = rand();
     44         o->size = 1;
     45     }
     46     else
     47     {
     48         int d = ( x <= o->v ? 0 : 1 );
     49         insert( o->ch[d], x );
     50         if ( o->ch[d]->r > o->r )
     51         {
     52             rotate( o, d ^ 1 );
     53         }
     54         else
     55         {
     56             o->maintain();
     57         }
     58     }
     59 }
     60 
     61 void remove( Node * & o, int x )
     62 {
     63     int d = o->cmp(x);
     64     if ( d == -1 )
     65     {
     66         if ( o->ch[0] != NULL && o->ch[1] != NULL )
     67         {
     68             int dd = ( o->ch[0]->r > o->ch[1]->r ? 1 : 0 );
     69             rotate( o, dd );
     70             remove( o->ch[dd], x );
     71         }
     72         else
     73         {
     74             Node * u = o;
     75             if ( o->ch[0] == NULL ) o = o->ch[1];
     76             else o = o->ch[0];
     77             delete u;
     78         }
     79     }
     80     else
     81     {
     82         remove( o->ch[d], x );
     83     }
     84     if ( o != NULL ) o->maintain();
     85 }
     86 
     87 int findm( Node * o, int d )
     88 {
     89     while ( o->ch[d] != NULL ) o = o->ch[d];
     90     return o->v;
     91 }
     92 
     93 int main ()
     94 {
     95     int n;
     96     while ( scanf("%d", &n) != EOF )
     97     {
     98         root = NULL;
     99         for ( int i = 0; i < n; i++ )
    100         {
    101             int op, x;
    102             scanf("%d", &op);
    103             if ( op == 1 )
    104             {
    105                 scanf("%d", &x);
    106                 insert( root, x );
    107             }
    108             else if ( op == 2 )
    109             {
    110                 if ( root != NULL )
    111                 {
    112                     x = findm( root, 0 );
    113                     remove( root, x );
    114                 }
    115             }
    116             else
    117             {
    118                 if ( root == NULL )
    119                 {
    120                     x = 0;
    121                 }
    122                 else
    123                 {
    124                     x = findm( root, 1 );
    125                 }
    126                 printf("%d
    ", x);
    127             }
    128         }
    129     }
    130     return 0;
    131 }
  • 相关阅读:
    趣味网站、趣味应用
    趣味网站、趣味应用
    论文写作的句型
    Python Tricks(二十一)—— 排列组合的计算
    Python Tricks(二十一)—— 排列组合的计算
    辨异 —— 有两人生日在同一天、只有两人生日在同一天
    辨异 —— 有两人生日在同一天、只有两人生日在同一天
    品味电影
    品味电影
    HDU 4414 Finding crosses (DFS + BFS)
  • 原文地址:https://www.cnblogs.com/huoxiayu/p/4702843.html
Copyright © 2020-2023  润新知