这个题其实有O(n)的算法,不过还是用线段树做了一遍,还写了个自认为不错的pushalldown函数,哈哈。
1 #include <iostream> 2 #include <cstring> 3 #include <cstdio> 4 using namespace std; 5 6 const int N = 100001; 7 int ans[N]; 8 9 struct Node 10 { 11 int l, r, add; 12 } node[N << 2]; 13 14 void build( int i, int l, int r ) 15 { 16 node[i].l = l, node[i].r = r, node[i].add = 0; 17 if ( l == r ) return ; 18 int lc = i << 1, rc = lc | 1, mid = ( l + r ) >> 1; 19 build( lc, l, mid ); 20 build( rc, mid + 1, r ); 21 } 22 23 void pushdown( int i ) 24 { 25 if ( node[i].add ) 26 { 27 int lc = i << 1, rc = lc | 1; 28 node[lc].add += node[i].add; 29 node[rc].add += node[i].add; 30 node[i].add = 0; 31 } 32 } 33 34 void update( int i, int l, int r ) 35 { 36 if ( node[i].l == l && node[i].r == r ) 37 { 38 node[i].add++; 39 return ; 40 } 41 //可以最后一起放下来 42 //pushdown(i); 43 int lc = i << 1, rc = lc | 1, mid = ( node[i].l + node[i].r ) >> 1; 44 if ( r <= mid ) 45 { 46 update( lc, l, r ); 47 } 48 else if ( l > mid ) 49 { 50 update( rc, l, r ); 51 } 52 else 53 { 54 update( lc, l, mid ); 55 update( rc, mid + 1, r ); 56 } 57 } 58 59 void pushalldown( int i ) 60 { 61 if ( node[i].l == node[i].r ) 62 { 63 ans[node[i].l] = node[i].add; 64 return ; 65 } 66 pushdown(i); 67 pushalldown( i << 1 ); 68 pushalldown( i << 1 | 1 ); 69 } 70 71 int main () 72 { 73 int n; 74 while ( scanf("%d", &n), n ) 75 { 76 build( 1, 1, n ); 77 for ( int i = 1; i <= n; i++ ) 78 { 79 int a, b; 80 scanf("%d%d", &a, &b); 81 update( 1, a, b ); 82 } 83 pushalldown(1); 84 for ( int i = 1; i <= n; i++ ) 85 { 86 printf("%d", ans[i]); 87 if ( i != n ) putchar(‘ ‘); 88 else putchar(‘\n‘); 89 } 90 } 91 return 0; 92 }
时间: 2024-10-14 13:26:36