hdu 1540 Tunnel Warfare(单点更新,取最大连续区间)★
2016-02-25 16:18
495 查看
题意是一条线上的点,D x是破坏这个点,Q x是表示查询以x所在的最长的连续的点的个数,R是恢复上一次破坏的点。
线段树结点 设置一个 ls 记录区间左端点开始的最大连续个数, rs 记录区间右端点开始的最大的连续个数,
ms表示该区间最大的连续点的个数。
线段树结点 设置一个 ls 记录区间左端点开始的最大连续个数, rs 记录区间右端点开始的最大的连续个数,
ms表示该区间最大的连续点的个数。
#include <algorithm> #include <iostream> #include <cstdio> #include <cstdlib> #include <string> #include <cstring> #include <cmath> #include <stack> #include <queue> #include <vector> #include <map> using namespace std; #define INF 0x3f3f3f3f #define maxn 50010 stack <int> s; struct node { int left,right; int ls,rs,ms; }tree[maxn<<2]; void build(int l,int r,int pos) { tree[pos].left = l; tree[pos].right = r; tree[pos].ls = tree[pos].rs = tree[pos].ms = r-l+1; if(l == r) return; int mid = (l+r)>>1; build(l,mid,pos<<1); build(mid+1,r,pos<<1|1); } void update(int pos,int k,int state) { if(tree[pos].left == tree[pos].right) { tree[pos].ls = tree[pos].rs = tree[pos].ms = state; return; } int mid = (tree[pos].left+tree[pos].right)>>1; if(k<=mid) update(pos<<1,k,state); else update(pos<<1|1,k,state); tree[pos].ls = tree[pos<<1].ls; tree[pos].rs = tree[pos<<1|1].rs; tree[pos].ms = max(max(tree[pos<<1].ms,tree[pos<<1|1].ms),tree[pos<<1].rs+tree[pos<<1|1].ls); if(tree[pos<<1].ls == tree[pos<<1].right-tree[pos<<1].left+1) tree[pos].ls += tree[pos<<1|1].ls; if(tree[pos<<1|1].rs == tree[pos<<1|1].right-tree[pos<<1|1].left+1) tree[pos].rs += tree[pos<<1].rs; } int query(int pos,int k) { if(tree[pos].ms==0 || tree[pos].ms==tree[pos].right-tree[pos].left+1 || tree[pos].left==tree[pos].right) return tree[pos].ms; int mid = (tree[pos].left+tree[pos].right)>>1; if(k <= tree[pos<<1|1].left+tree[pos<<1|1].ls-1 && k >= tree[pos<<1].right-tree[pos<<1].rs+1) return tree[pos<<1].rs+tree[pos<<1|1].ls; else if(k <= mid) return query(pos<<1,k); else if(k > mid) return query(pos<<1|1,k);/* if(k<=mid) { if(k>=tree[pos<<1].right-tree[pos<<1].rs+1) return query(pos<<1,k)+query(pos<<1|1,mid+1); else return query(pos<<1,k); } else { if(k<=tree[pos<<1|1].left+tree[pos<<1|1].ls-1) return query(pos<<1|1,k)+query(pos<<1,mid); else return query(pos<<1|1,k); }*/ } int main() { int n,m; while(scanf("%d%d",&n,&m)!=EOF) { build(1,n,1); s.empty(); char c; int x; for(int i = 0; i < m; i++) { getchar(); scanf("%c",&c); if(c == 'D') { scanf("%d",&x); update(1,x,0); s.push(x); } else if(c == 'Q') { scanf("%d",&x); printf("%d\n",query(1,x)); } else { update(1,s.top(),1); s.pop(); } } } return 0; }
相关文章推荐
- Java华容道
- java,for穷举,经典题目,百鸡百钱
- MFC 运行日志
- JSON解析的理解
- Android 5.0 CardView 笔记
- eclipse 和android studio 导入github项目
- 字符串连接
- mysql windows下忘记root密码
- 【设计模式】模板方法模式
- Redis的windows安装
- c++屏幕截图
- C++ 拆分字符串-
- Valid Parentheses
- swift 闭包
- python学习第十五课 --jquery 续
- iOS下的实际网络连接状态检测
- 升级到XCode7后出现 <Error>: CGContextSaveGState: invalid context 0x0.
- android:clipToPadding和android:clipChildren
- Git使用之设置SSH Key
- 很惨的25分钟