HDU 1540 Tunnel Warfare
2013-05-22 09:50
337 查看
线段树点修改+区间合并
对于如何查询连续某块的端点和长度还不太熟……但是属于经典常见操作。
对于如何查询连续某块的端点和长度还不太熟……但是属于经典常见操作。
#include <cstdio> #include <cstring> #include <cstdlib> #include <algorithm> using namespace std; #define lc rt << 1 #define rc rt << 1 | 1 #define lson l, m, rt << 1 #define rson m + 1, r, rt << 1 | 1 const int MAXN = 50002; int N, Q; int stack[MAXN]; int top; int len[ MAXN << 2 ]; int Llen[ MAXN << 2 ]; int Rlen[ MAXN << 2 ]; bool lbd[ MAXN << 2 ]; bool rbd[ MAXN << 2 ]; void PushUp( int rt, int l, int r, int m ) { len[rt] = max( len[lc], len[rc] ); if ( rbd[lc] && lbd[rc] ) len[rt] = max( len[rt], Llen[rc] + Rlen[lc] ); lbd[rt] = lbd[lc]; rbd[rt] = rbd[rc]; Llen[rt] = Llen[lc]; Rlen[rt] = Rlen[rc]; if ( Llen[lc] == m - l + 1 ) Llen[rt] += Llen[rc]; if ( Rlen[rc] == r - m ) Rlen[rt] += Rlen[lc]; return; } void build( int l, int r, int rt ) { if ( l == r ) { lbd[rt] = rbd[rt] = true; len[rt] = 1; Llen[rt] = Rlen[rt] = 1; return; } int m = ( l + r ) >> 1; build( lson ); build( rson ); PushUp( rt, l, r, m ); return; } void Update( int L, int c, int l, int r, int rt ) { if ( L == l && L == r ) { len[rt] = Llen[rt] = Rlen[rt] = c; if ( c == 1 ) lbd[rt] = rbd[rt] = true; else lbd[rt] = rbd[rt] = false; return; } int m = ( l + r ) >> 1; if ( L <= m ) Update( L, c, lson ); else Update( L, c, rson ); PushUp( rt, l, r, m ); return; } int Query( int L, int l, int r, int rt ) { if ( l == r || !len[rt] || len[rt] == r - l + 1 ) return len[rt]; int m = ( l + r ) >> 1; if ( L <= m ) { if ( L > m - Rlen[lc] ) return Query( L, lson ) + Query( m + 1, rson ); else return Query( L, lson ); } else { if ( L < m + 1 + Llen[rc] ) return Query( m, lson ) + Query( L, rson ); else return Query( L, rson ); } } int main() { //freopen( "in.txt", "r", stdin ); //freopen( "out.txt", "w", stdout ); while ( ~scanf( "%d%d", &N, &Q ) ) { build( 1, N, 1 ); top = 0; while ( Q-- ) { char str[4]; scanf( "%s", str ); if ( str[0] == 'R' ) { if ( top > 0 ) Update( stack[top--], 1, 1, N, 1 ); } else { int a; scanf( "%d", &a ); if ( str[0] == 'D' ) { Update( a, 0, 1, N, 1 ); stack[ ++top ] = a; } else printf( "%d\n", Query( a, 1, N, 1 ) ); } } } return 0; }
相关文章推荐
- I - Tunnel Warfare - hdu 1540(区间合并更新)
- 线段树专辑——hdu 1540 Tunnel Warfare
- hdu 1540 Tunnel Warfare 一个关于线段的故事~~~线段树是我无法言明的伤~
- HDU 1540——Tunnel Warfare
- HDU 1540 Tunnel Warfare (线段树)
- HDU 1540 Tunnel Warfare
- HDU 1540 Tunnel Warfare(线段树区间合并)
- multiset运用 HDU 1540 Tunnel Warfare
- HDU1540-Tunnel Warfare
- hdu1540 Tunnel Warfare(线段树)(好题)
- hdu 1540 Tunnel Warfare(线段树区间统计)
- hdu 1540 Tunnel Warfare
- hdu 1540 Tunnel Warfare
- (两种解法)hdu 1540 Tunnel Warfare (线段树区间合并)
- hdu 1540 Tunnel Warfare (线段树维护左右最长连续区间)
- I - Tunnel Warfare - hdu 1540
- HDU 1540 Tunnel Warfare [二分 + 线段树]
- 【维护区间最长连续子序列 && 线段树 && 区间归并】HDU - 1540 Tunnel Warfare
- HDU1540 Tunnel Warfare(线段树:维护最大连续子串)
- ACM 数据结构 线段树 HDU 1540 Tunnel Warfare