[主席树区间覆盖 线段树] UNR #1 火车管理
来源:互联网 发布:软件的健壮性 编辑:程序博客网 时间:2024/06/05 19:14
火车管理
我们可以建立一颗可持久化线段树,维护每个铁路每个时间的栈顶的吨位和栈顶火车的入栈时间。
我们再维护一颗线段树用来统计答案。
于是操作就显得很简单了:
区间询问:直接在答案线段树里询问即可。
区间压数:在可持久化线段树上进行区间覆盖,这个是十分基础的数据结构技巧,然后在答案线段树上修改一下。
区间弹数:由于我们记录了入栈时间,所以我们删完后用可持久化线段树查出当前入栈之前的栈顶的信息即可,然后在答案线段树上和可持久化线段树上修改一下。
大概理解下 然后自己YY出一个主席树区间覆盖
#include<cstdio>#include<cstdlib>#include<algorithm>#define dprintf(...) fprintf(stderr,__VA_ARGS__)using namespace std;inline char nc(){static char buf[100000],*p1=buf,*p2=buf;if (p1==p2) { p2=(p1=buf)+fread(buf,1,100000,stdin); if (p1==p2) return EOF; }return *p1++;}inline void read(int &x){char c=nc(),b=1;for (;!(c>='0' && c<='9');c=nc()) if (c=='-') b=-1;for (x=0;c>='0' && c<='9';x=x*10+c-'0',c=nc()); x*=b;}const int N=500005;const int M=30000005;int n;namespace ZXT{int ncnt;int root[N];int ls[M],rs[M],Fla[M];inline void build(int &x,int l,int r){x=++ncnt; int mid=(l+r)>>1;if (l==r) return;build(ls[x],l,mid);build(rs[x],mid+1,r);}inline void modify(int &x,int y,int l,int r,int ql,int qr,int qf,int flag){if (r<ql || l>qr){if (!flag)x=y;else{x=++ncnt;ls[x]=ls[y]; rs[x]=rs[y];Fla[x]=flag;}return;}if (ql<=l && r<=qr){x=++ncnt;ls[x]=ls[y]; rs[x]=rs[y];Fla[x]=qf;return;}x=++ncnt;int mid=(l+r)>>1;if (!flag && Fla[y]) flag=Fla[y];modify(ls[x],ls[y],l,mid,ql,qr,qf,flag);modify(rs[x],rs[y],mid+1,r,ql,qr,qf,flag);}inline int query(int x,int l,int r,int t){if (Fla[x] || l==r) return Fla[x];int mid=(l+r)>>1;if (t<=mid)query(ls[x],l,mid,t);elsequery(rs[x],mid+1,r,t);}inline void Print(int x){for (int i=1;i<=n;i++) dprintf("%d ",query(root[x],1,n,i)); dprintf("\n");}}int T[N<<2],F[N<<2];inline void Build(int rt,int l,int r){F[rt]=-1; int mid=(l+r)>>1; if (l==r) return;Build(rt<<1,l,mid); Build(rt<<1|1,mid+1,r);}inline void Modify(int rt,int l,int r,int ql,int qr,int qt){if (ql<=l && r<=qr){T[rt]=qt*(r-l+1);F[rt]=qt;return;}int mid=(l+r)>>1;if (F[rt]!=-1){T[rt<<1]=F[rt]*(mid-l+1);T[rt<<1|1]=F[rt]*(r-mid);F[rt<<1]=F[rt<<1|1]=F[rt];F[rt]=-1;}if (ql<=mid) Modify(rt<<1,l,mid,ql,qr,qt);if (qr>mid) Modify(rt<<1|1,mid+1,r,ql,qr,qt);T[rt]=T[rt<<1]+T[rt<<1|1];}inline int Query(int rt,int l,int r,int ql,int qr){if (ql<=l && r<=qr)return T[rt];int mid=(l+r)>>1;if (F[rt]!=-1){T[rt<<1]=F[rt]*(mid-l+1);T[rt<<1|1]=F[rt]*(r-mid);F[rt<<1]=F[rt<<1|1]=F[rt];F[rt]=-1;}int ret=0;if (ql<=mid) ret+=Query(rt<<1,l,mid,ql,qr);if (qr>mid) ret+=Query(rt<<1|1,mid+1,r,ql,qr);return ret;}int ton[N];int main(){using namespace ZXT;int lastans=0,ty,Q;int l,r,t,order;freopen("t.in","r",stdin);freopen("t.out","w",stdout);read(n); read(Q); read(ty);Build(1,1,n);build(root[0],1,n);//Print(0);for (int clk=1;clk<=Q;clk++){read(order);if (order==1){read(l); read(r);l=(l+lastans*ty)%n+1; r=(r+lastans*ty)%n+1; if (r<l) swap(l,r);lastans=Query(1,1,n,l,r);printf("%d\n",lastans);root[clk]=root[clk-1];}else if (order==2){read(l);l=(l+lastans*ty)%n+1;int last=query(root[clk-1],1,n,l);if (!last) { root[clk]=root[clk-1]; continue; }last=query(root[last-1],1,n,l);Modify(1,1,n,l,l,ton[last]);modify(root[clk],root[clk-1],1,n,l,l,last,0);ton[clk]=last;}else{read(l); read(r); read(t);l=(l+lastans*ty)%n+1; r=(r+lastans*ty)%n+1; if (r<l) swap(l,r);Modify(1,1,n,l,r,t); ton[clk]=t;modify(root[clk],root[clk-1],1,n,l,r,clk,0);}//Print(clk);}return 0;}
0 0
- [主席树区间覆盖 线段树] UNR #1 火车管理
- 【UOJ #218. 【UNR #1】】火车管理 可持久化线段树
- UOJ#218 【UNR #1】火车管理
- 线段树--区间覆盖
- [线段树 单调栈] UNR #1 争夺圣杯
- [下界最小流] UNR #1 奇怪的线段树
- UOJ#217. 【UNR #1】奇怪的线段树
- POJ2528 线段树区间覆盖
- 线段树 区间覆盖 区间增加
- Python 线段树求区间覆盖
- poj 2777 Count 线段树区间覆盖
- 线段树解决区间覆盖问题
- hdu3577-Fast Arrangement 线段树区间覆盖
- POJ1436 Horizontally Visible Segments 线段树区间更新--区间覆盖
- Astar Round2B 1005 区间交 区间覆盖 线段树
- hdu 3397 Sequence operation(线段树区间覆盖,区间合并)
- HihoCoder 1078(线段树,区间覆盖 询问区间和)
- 【HDU4348】To The Moon-主席树(可持久化线段树)区间修改+区间询问
- orbslam2的基础理论(一)
- 如何理解BGP同步规则-
- HTML特殊字符的html、js、css写法汇总
- Makefile (三) 总述
- Git命令行下自动保存用户名和密码
- [主席树区间覆盖 线段树] UNR #1 火车管理
- Android短信发送,监听,及其工具类封装
- ubuntu14.04系统相关
- Spark 源码解析 : DAGScheduler中的DAG划分与提交
- 转义字符
- UIProgressView 进度表
- IO
- APUE 8-1 fork函数实例
- 【嵌入式学习日记】2016年7月19日