poj的中文题哦
果然不是容易写的
光是几个运算符就很让人 头疼
我们来看一看
让求最后集合里的数。
可这么多运算怎么弄
需要转换一下喽
一开始有一个大的区间0-maxn
U:把区间[l,r]覆盖成1
I:把[-∞,l)(r,∞]覆盖成0
D:把区间[l,r]覆盖成0
C:把[-∞,l)(r,∞]覆盖成0 , 且[l,r]区间0/1互换
S:[l,r]区间0/1互换‘
所以问题演变成覆盖和xor的线段树嗯哼!
但是第一次写 越界问题没有注意。。
#include<cstdio>
#include<algorithm>
#include<cstring>
#define maxn 666666
//#define maxn 10<<1
using namespace std;
//by mars_ch
//感谢SiriusRen爸爸
/*
U:把区间[l,r]覆盖成1
I:把[-∞,l)(r,∞]覆盖成0
D:把区间[l,r]覆盖成0
C:把[-∞,l)(r,∞]覆盖成0 , 且[l,r]区间0/1互换
S:[l,r]区间0/1互换
*/
int cover[maxn<<2];//覆盖标记
int rev[maxn<<2];//翻转
int vis[maxn<<2];
void pushdown(int x)
{
if(cover[x]!=-1)
{
cover[x*2]=cover[x*2+1]=cover[x];
rev[x*2]=rev[x*2+1]=0;
cover[x]=-1;//完成覆盖标记
}
if(rev[x])
{
if(cover[x*2]!=-1) cover[x*2]^=1;
else rev[x*2]^=1;
rev[x]=0;
if(cover[x*2+1]!=-1) cover[x*2+1]^=1;
else rev[x*2+1]^=1;
rev[x]=0;
}
}
void updata(int op,int L,int R,int l,int r,int num)
{
//printf("%d %d %d %d\n",l,r,L,R);
if(l<L || r>R) return;
//printf("twice %d %d %d %d\n",l,r,L,R);
//printf(" llalaal\n");
if(l == L && r ==R)
{
if(op!=-1)//不是覆盖操作 ,当一个节点得到覆盖标记后,翻转标记清空
{
//printf("%d %d %d %d\n",num,op,l,r);
cover[num]=op;
rev[num]=0;
}
else
{
if(cover[num]!=-1) cover[num]^=1; //如果区间都是0或者1那就直接改变覆盖
else rev[num]^=1; //不然该翻转标记
}
return;
}
pushdown(num);
int mid=(L+R)/2;
if(r<=mid) updata(op,L,mid,l,r,num*2);
else if(l>mid) updata(op,mid+1,R,l,r,num*2+1);//l>mid不是>=
else
{
updata(op,L,mid,l,mid,num*2);
updata(op,mid+1,R,mid+1,r,num*2+1);
}
}
void query(int l,int r,int x)
{
if(cover[x] == 1)
{
for(int i=l;i<=r;i++)
{
vis[i]=true;
}
return ;
}
else if(cover[x] == 0) return;
if(l == r) return ;
pushdown(x);
int mid=(l+r)/2;
query(l,mid,x*2);
query(mid+1,r,x*2+1);
}
int main()
{
char c;
char b,d;
int x,y;
while(scanf("%c %c%d,%d%c\n",&c,&b,&x,&y,&d)!=EOF)
{
x*=2,y*=2;
if(b == '(') x++;
if(d == ')') y--;
if(x>y)x=y=150000; //非法情况
//printf("%d %d\n",x,y);
if( c == 'U') updata(1,0,maxn,x,y,1);
else if(c == 'D') updata(0,0,maxn,x,y,1);
else if(c == 'I')
{
if(x)updata(0,0,maxn,0,x-1,1); //数组越界
updata(0,0,maxn,y+1,maxn,1);
}
else if(c == 'C')
{
if(x)updata(0,0,maxn,0,x-1,1);
updata(0,0,maxn,y+1,maxn,1);
updata(-1,0,maxn,x,y,1);
}
else if(c == 'S')
{
updata(-1,0,maxn,x,y,1);
}
}
query(0,maxn,1);
/*for(int i=0;i<=20;i++)
{
printf("%d ",vis[i]);
}
puts("");*/
int s=-1,e;
bool flag=0;
for(int i=0;i<=146666;i++)
{
if(vis[i])
{
if(s == -1)
{
s=i;
}
e=i;
}
else
{
if(s == -1) continue;
if(flag) printf(" ");
printf("%c%d,%d%c",s&1?'(':'[',s>>1,(e+1)>>1,e&1?')':']');
s=-1;
flag=1;
}
}
if(!flag) printf("empty set\n");
else puts("");
return 0;
}