zoj 3279 线段树 OR 树状数组

其实就是找一个最小的level k使得level 1到k的ant数量和不小于rank。

树状数组:

 1 #include <iostream>
 2 #include <cstring>
 3 #include <cstdio>
 4 using namespace std;
 5 
 6 const int N = 100001;
 7 int a[N];
 8 int c[N];
 9 int n, m;
10 
11 int lb( int i )
12 {
13     return i & -i;
14 }
15 
16 void update( int i, int v )
17 {
18     while ( i <= n )
19     {
20         c[i] += v;
21         i += lb(i);
22     }
23 }
24 
25 int kth( int k )
26 {
27     int ans = 0, cnt = 0;
28     for ( int i = 16; i >= 0; i-- )
29     {
30         ans += ( 1 << i );
31         if ( ans >= n || cnt + c[ans] >= k )
32         {
33             ans -= ( 1 << i );
34         }
35         else
36         {
37             cnt += c[ans];
38         }
39     }
40     return ans + 1;
41 }
42 
43 int main ()
44 {
45     while ( scanf("%d", &n) != EOF )
46     {
47         memset( c, 0, sizeof(c) );
48         for ( int i = 1; i <= n; i++ )
49         {
50             scanf("%d", a + i);
51             update( i, a[i] );            
52         }
53         scanf("%d", &m);
54         while ( m-- )
55         {
56             char op[2];
57             int x, y;
58             scanf("%s", op);
59             if ( op[0] == 'q' )
60             {
61                 scanf("%d", &x);
62                 printf("%d\n", kth(x));
63             }
64             else
65             {
66                 scanf("%d%d", &x, &y);
67                 update( x, y - a[x] );
68                 a[x] = y;
69             }
70         }
71     }
72     return 0;
73 }

线段树:

 1 #include <iostream>
 2 #include <cstring>
 3 #include <cstdio>
 4 using namespace std;
 5 
 6 const int N = 100001;
 7 int a[N];
 8 int n, m;
 9 
10 struct Node 
11 {
12     int l, r, sum;
13 } node[N << 2];
14 
15 void pushup( int i )
16 {
17     node[i].sum = node[i << 1].sum + node[i << 1 | 1].sum;
18 }
19 
20 void build( int i, int l, int r )
21 {
22     node[i].l = l, node[i].r = r;
23     if ( l == r )
24     {
25         node[i].sum = a[l];
26         return ;
27     }
28     int mid = ( l + r ) >> 1;    
29     build( i << 1, l, mid );
30     build( i << 1 | 1, mid + 1, r );
31     pushup(i);
32 }
33 
34 void update( int i, int pos, int val )
35 {
36     if ( node[i].l == pos && node[i].r == pos )
37     {
38         node[i].sum = val;
39         return ;
40     }
41     int mid = ( node[i].l + node[i].r ) >> 1;
42     if ( pos <= mid )
43     {
44         update( i << 1, pos, val );
45     }
46     else
47     {
48         update( i << 1 | 1, pos, val );
49     }
50     pushup(i);
51 }
52 
53 int query( int i, int v )
54 {
55     if ( node[i].l == node[i].r ) return node[i].l;
56     if ( node[i << 1].sum >= v ) return query( i << 1, v );
57     return query( i << 1 | 1, v - node[i << 1].sum );
58 }
59 
60 int main ()
61 {
62     while ( scanf("%d", &n) != EOF )
63     {
64         for ( int i = 1; i <= n; i++ )
65         {
66             scanf("%d", a + i);
67         }
68         build( 1, 1, n );
69         scanf("%d", &m);
70         while ( m-- )
71         {
72             char op[2];
73             int x, y;
74             scanf("%s", op);
75             if ( op[0] == 'q' )
76             {
77                 scanf("%d", &x);
78                 printf("%d\n", query( 1, x ));
79             }
80             else
81             {
82                 scanf("%d%d", &x, &y);
83                 update( 1, x, y );
84             }
85         }
86     }
87     return 0;
88 }

 

posted @ 2015-08-18 20:07  hxy_has_been_used  阅读(113)  评论(0)    收藏  举报