BZOJ2636: crisis(可持久化线段树)
解题思路:
题目描述是一大坑点,cancel后面是直接加ask或者redo的。
那么就可以愉快地可持久化了。
注意需要支持区间修改,那么就只需要在再次更新这个点的时候将标记储存在新的儿子中。
最后由下至上询问就好了。
代码:
#include<cmath>
#include<cstdio>
#include<cstring>
#include<algorithm>
typedef double dnt;
const double eps=1e-;
struct trnt{
int ls;
int rs;
double dltx,dlty;
double alpha;
bool lunked;
}tr[];
struct pnt{
double x,y;
void insert(void)
{
scanf("%lf%lf",&x,&y);
return ;
}
}p[];
int siz;
int cnt;
int n,m;
char cmd[];
int root[];
void move(int spc,double dx,double dy)
{
tr[spc].dltx+=dx;
tr[spc].dlty+=dy;
return ;
}
void patrol(int spc,double beta)
{
tr[spc].alpha+=beta;
double nx,ny,x,y;
x=tr[spc].dltx,y=tr[spc].dlty;
nx=x*cos(beta)-y*sin(beta);
ny=y*cos(beta)+x*sin(beta);
tr[spc].dltx=nx;
tr[spc].dlty=ny;
return ;
}
void lunk(int spc)
{
tr[spc].alpha=tr[spc].dltx=tr[spc].dlty=;
tr[spc].lunked=true;
return ;
}
void pushdown(int spc,int lst)
{
tr[++siz]=tr[tr[lst].ls];
tr[spc].ls=siz;
tr[++siz]=tr[tr[lst].rs];
tr[spc].rs=siz;
if(tr[spc].lunked)
{
lunk(tr[spc].ls);
lunk(tr[spc].rs);
}
patrol(tr[spc].ls,tr[spc].alpha);
patrol(tr[spc].rs,tr[spc].alpha);
move(tr[spc].ls,tr[spc].dltx,tr[spc].dlty);
move(tr[spc].rs,tr[spc].dltx,tr[spc].dlty);
tr[spc].lunked=false;
tr[spc].alpha=tr[spc].dltx=tr[spc].dlty=;
return ;
}
void build(int l,int r,int &spc)
{
spc=++siz;
if(l==r)return ;
int mid=(l+r)>>;
build(l,mid,tr[spc].ls);
build(mid+,r,tr[spc].rs);
return ;
}
void Move(int l,int r,int ll,int rr,int spc,int lst,double dx,double dy)
{
if(!spc)return ;
if(ll>r||l>rr)return ;
if(ll<=l&&r<=rr)
{
move(spc,dx,dy);
return ;
}
int mid=(l+r)>>;
pushdown(spc,lst);
Move(l,mid,ll,rr,tr[spc].ls,tr[lst].ls,dx,dy);
Move(mid+,r,ll,rr,tr[spc].rs,tr[lst].rs,dx,dy);
return ;
}
void Patrol(int l,int r,int ll,int rr,int spc,int lst,double beta)
{
if(!spc)return ;
if(ll>r||l>rr)return ;
if(ll<=l&&r<=rr)
{
patrol(spc,beta);
return ;
}
int mid=(l+r)>>;
pushdown(spc,lst);
Patrol(l,mid,ll,rr,tr[spc].ls,tr[lst].ls,beta);
Patrol(mid+,r,ll,rr,tr[spc].rs,tr[lst].rs,beta);
return ;
}
void Lunk(int l,int r,int ll,int rr,int spc,int lst)
{
if(!spc)return ;
if(ll>r||l>rr)return ;
if(ll<=l&&r<=rr)
{
lunk(spc);
return ;
}
int mid=(l+r)>>;
pushdown(spc,lst);
Lunk(l,mid,ll,rr,tr[spc].ls,tr[lst].ls);
Lunk(mid+,r,ll,rr,tr[spc].rs,tr[lst].rs);
return ;
}
void query(int l,int r,int spc,int pos,double &x,double &y)
{
if(!spc)return ;
if(l>r)return ;
int mid=(l+r)>>;
if(pos<=mid)query(l,mid,tr[spc].ls,pos,x,y);
else query(mid+,r,tr[spc].rs,pos,x,y);
if(tr[spc].lunked)x=y=;
if(fabs(tr[spc].alpha)>eps)
{
double nx,ny;
nx=x*cos(tr[spc].alpha)-y*sin(tr[spc].alpha);
ny=y*cos(tr[spc].alpha)+x*sin(tr[spc].alpha);
x=nx,y=ny;
}
x+=tr[spc].dltx;
y+=tr[spc].dlty;
return ;
}
int main()
{
// freopen("zoo.in","r",stdin);
// freopen("zoo.out","w",stdout);
scanf("%d",&n);
for(int i=;i<=n;i++)p[i].insert();
scanf("%d",&m);
cnt=;
build(,n,root[cnt]);
while(m--)
{
scanf("%s",cmd+);
if(cmd[]=='M')
{
int l,r;
scanf("%d%d",&l,&r);
if(l>r)std::swap(l,r);
double dx,dy;
scanf("%lf%lf",&dx,&dy);
tr[++siz]=tr[root[cnt]];
root[++cnt]=siz;
Move(,n,l,r,root[cnt],root[cnt-],dx,dy);
}
if(cmd[]=='P')
{
int l,r;
scanf("%d%d",&l,&r);
double beta;
scanf("%lf",&beta);
if(l>r)std::swap(l,r);
tr[++siz]=tr[root[cnt]];
root[++cnt]=siz;
Patrol(,n,l,r,root[cnt],root[cnt-],beta);
}
if(cmd[]=='L')
{
int l,r;
scanf("%d%d",&l,&r);
if(l>r)std::swap(l,r);
tr[++siz]=tr[root[cnt]];
root[++cnt]=siz;
Lunk(,n,l,r,root[cnt],root[cnt-]);
}
if(cmd[]=='C')
{
int a;
scanf("%d",&a);
cnt-=a;
}
if(cmd[]=='R')
{
int a;
scanf("%d",&a);
cnt+=a;
}
if(cmd[]=='A')
{
int pos;
scanf("%d",&pos);
double x=p[pos].x,y=p[pos].y;
query(,n,root[cnt],pos,x,y);
printf("%.6lf %.6lf\n",x,y);
}
}
return ;
}
BZOJ2636: crisis(可持久化线段树)的更多相关文章
- PYOJ 44. 【HNSDFZ2016 #6】可持久化线段树
#44. [HNSDFZ2016 #6]可持久化线段树 统计 描述 提交 自定义测试 题目描述 现有一序列 AA.您需要写一棵可持久化线段树,以实现如下操作: A v p x:对于版本v的序列,给 A ...
- 【BZOJ-3673&3674】可持久化并查集 可持久化线段树 + 并查集
3673: 可持久化并查集 by zky Time Limit: 5 Sec Memory Limit: 128 MBSubmit: 1878 Solved: 846[Submit][Status ...
- 【BZOJ-2653】middle 可持久化线段树 + 二分
2653: middle Time Limit: 20 Sec Memory Limit: 512 MBSubmit: 1298 Solved: 734[Submit][Status][Discu ...
- HDU 4866 Shooting(持久化线段树)
view code//第二道持久化线段树,照着别人的代码慢慢敲,还是有点不理解 #include <iostream> #include <cstdio> #include & ...
- 【BZOJ-3653】谈笑风生 DFS序 + 可持久化线段树
3653: 谈笑风生 Time Limit: 20 Sec Memory Limit: 512 MBSubmit: 628 Solved: 245[Submit][Status][Discuss] ...
- 【BZOJ3673】&&【BZOJ3674】: 可持久化并查集 by zky 可持久化线段树
没什么好说的. 可持久化线段树,叶子节点存放父亲信息,注意可以规定编号小的为父亲. Q:不是很清楚空间开多大,每次询问父亲操作后修改的节点个数是不确定的.. #include<bits/stdc ...
- 【BZOJ3207】花神的嘲讽计划I 可持久化线段树/莫队
看到题目就可以想到hash 然后很自然的联想到可持久化权值线段树 WA:base取了偶数 这道题还可以用莫队做,比线段树快一些 可持久化线段树: #include<bits/stdc++.h&g ...
- 【BZOJ 3674】可持久化并查集加强版&【BZOJ 3673】可持久化并查集 by zky 用可持久化线段树破之
最后还是去掉异或顺手A了3673,,, 并查集其实就是fa数组,我们只需要维护这个fa数组,用可持久化线段树就行啦 1:判断是否属于同一集合,我加了路径压缩. 2:直接把跟的值指向root[k]的值破 ...
- 【BZOJ 3524】【Poi2014】Couriers 可持久化线段树
为什么这个主席树叫可持久化线段树,我不知道,具体得问达神.我无限T,然后DaD3zZ一针见血地指出了我的N*50爆内存导致无限编译超时O)ZO)ZO)Z真是太神啦.以图为鉴: 达神题解传送门:http ...
随机推荐
- zoj 1655 单源最短路 改为比例+最长路
http://acm.zju.edu.cn/onlinejudge/showProblem.do? problemId=655 没有理解清题意就硬套模板.所以WA了好几次. 解析看我的还有一篇http ...
- <<Python基础教程>>学习笔记 | 第12章 | 图形用户界面
Python支持的工具包非常多.但没有一个被觉得标准的工具包.用户选择的自由度大些.本章主要介绍最成熟的跨平台工具包wxPython.官方文档: http://wxpython.org/ ------ ...
- PIC18F4520 + NRF24L01
SI SO应该对调过来用.. TX /* ** Tx.c ** Transmit test program for PIC18F4520 and nRF24L01 or nRF24L01+ ** Us ...
- [NOIP2015模拟10.27] 挑竹签 解题报告(拓扑排序)
Description 挑竹签——小时候的游戏夏夜,早苗和诹访子在月光下玩起了挑竹签这一经典的游戏.挑竹签,就是在桌上摆上一把竹签,每次从最上层挑走一根竹签.如果动了其他的竹签,就要换对手来挑.在所有 ...
- Spring控制反转容器的使用例子
详细代码如下: spring-config.xml <?xml version="1.0" encoding="UTF-8"?> <beans ...
- 把asp:CheckBoxList 变成单选框
单选框代码 <asp:CheckBoxList runat="server" RepeatDirection="Horizontal" ID=" ...
- <Sicily>Polynomial
一.题目描述 Given a polynomial and the value of the variable x, you task is to calculate the value of the ...
- ES6学习5 字符串的扩展
1.ES6 为字符串添加了遍历器接口,使得字符串可以被for...of循环遍历. for (let codePoint of 'foo') { console.log(codePoint) } // ...
- Python学习七步走
在周五的下午三点钟(为什么是这个时间?因为事情总会在周五下午三点钟发生),你收到一条通知,客户发现你的软件出现一个错误.在有了初步的怀疑后,你联系运维,查看你的软件日志以了解发生了什么,因为你记得收到 ...
- screen---管理会话
Screen是一款由GNU计划开发的用于命令行终端切换的自由软件.用户可以通过该软件同时连接多个本地或远程的命令行会话,并在其间自由切换.GNU Screen可以看作是窗口管理器的命令行界面版本.它提 ...