zoj 1610 线段树

用线段树进行区间赋值,最后将每个小segment的颜色求出来,再扫一遍判断连续的段数即可。

  1 #include <iostream>
  2 #include <cstring>
  3 #include <cstdio>
  4 using namespace std;
  5 
  6 const int N = 8001;
  7 int color[N];
  8 int ans[N];
  9 
 10 struct Node 
 11 {
 12     int l, r, c;
 13 } node[N << 2];
 14 
 15 void build( int i, int l, int r )
 16 {
 17     node[i].l = l, node[i].r = r, node[i].c = -1;
 18     if ( l == r ) return ;
 19     int mid = ( l + r ) >> 1;
 20     build( i << 1, l, mid );
 21     build( i << 1 | 1, mid + 1, r );
 22 }
 23 
 24 void pushdown( int i )
 25 {
 26     if ( node[i].c != -1 )
 27     {
 28         node[i << 1].c = node[i << 1 | 1].c = node[i].c;
 29         node[i].c = -1;
 30     }
 31 }
 32 
 33 void update( int i, int l, int r, int c )
 34 {
 35     if ( node[i].l == l && node[i].r == r )
 36     {
 37         node[i].c = c;
 38         return ;
 39     }
 40     pushdown(i);
 41     int mid = ( node[i].l + node[i].r ) >> 1;
 42     if ( r <= mid )
 43     {
 44         update( i << 1, l, r, c );
 45     }    
 46     else if ( l > mid )
 47     {
 48         update( i << 1 | 1, l, r, c );
 49     }
 50     else
 51     {
 52         update( i << 1, l, mid, c );
 53         update( i << 1 | 1, mid + 1, r, c );
 54     }
 55 }
 56 
 57 void pushalldown( int i )
 58 {
 59     if ( node[i].l == node[i].r )
 60     {
 61         if ( node[i].c != -1 )
 62         {
 63             color[node[i].l] = node[i].c;
 64         }
 65         return ;
 66     }
 67     pushdown(i);
 68     pushalldown( i << 1 );
 69     pushalldown( i << 1 | 1 );
 70 }
 71 
 72 int main ()
 73 {
 74     int n;
 75     while ( scanf("%d", &n) != EOF )
 76     {
 77         build( 1, 1, 8000 );
 78         for ( int i = 1; i <= n; i++ )
 79         {
 80             int x, y, z;
 81             scanf("%d%d%d", &x, &y, &z);
 82             update( 1, x + 1, y, z );
 83         }
 84         memset( color, -1, sizeof(color) );
 85         pushalldown(1);
 86         memset( ans, 0, sizeof(ans) );
 87         for ( int i = 1; i <= 8000; i++ )
 88         {
 89             if ( color[i] == -1 ) continue;
 90             ans[color[i]]++;
 91             while ( i + 1 <= 8000 && color[i] == color[i + 1] )
 92             {
 93                 i++;
 94             }
 95         }
 96         for ( int i = 0; i <= 8000; i++ )
 97         {
 98             if ( ans[i] )
 99             {
100                 printf("%d %d
", i, ans[i]);
101             }
102         }
103         putchar('
');
104     }
105     return 0;
106 }
原文地址:https://www.cnblogs.com/huoxiayu/p/4779944.html