标签:
---恢复内容开始---
【题目大意】
(直接引用ACM神犇概括,貌似是notonlysucess?)
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互换
【思路】
由于涉及到开区间和闭区间,我们如此规定数组下表:
下标 0 1 2 3 4 5……
含义1 (1 1 (2 2 (3 3……
含义2 / / 1) / 2) /……
cover表示区间覆盖,Xor表示区间取反。
如果cover要直接覆盖的话,Xor的值就没有意义了,可以清为0;如果要区间取反的话,如果cover有值则将cover取反,否则就将Xor取反。注意一下边界……
QuQ死磕了一个上午才搞定,后来才发现原来我忘记把freopen的语句删掉了!痛彻心扉,从此铭记,不再犯!
1 /*模板来自于notonlysuccess*/ 2 #include<iostream> 3 #include<cstdio> 4 #include<algorithm> 5 #include<cstring> 6 #define lson l,m,rt<<1 7 #define rson m+1,r,rt<<1|1 8 using namespace std; 9 const int MAXN=65536*2; 10 int cover[MAXN<<2];//-1里面不确定,0覆盖0,1覆盖1 11 int Xor[MAXN<<2];//0表示区间取反过来,1表示区间不取反 12 int hash[MAXN+1]; 13 14 void Fxor(int rt)//对rt进行01对调 15 { 16 if (cover[rt]!=-1) 17 { 18 cover[rt]^=1; 19 } 20 else Xor[rt]^=1; 21 } 22 23 24 void pushdown(int rt) 25 { 26 if (cover[rt]!=-1) 27 { 28 cover[rt<<1]=cover[rt<<1|1]=cover[rt]; 29 Xor[rt<<1]=Xor[rt<<1|1]=0; 30 cover[rt]=-1;//由于cover的值已经给两个孩子,此时将cover设为-1 31 } 32 if (Xor[rt]) 33 { 34 Fxor(rt<<1); 35 Fxor(rt<<1|1); 36 Xor[rt]=0;//由于已经将Xor的值给两个孩子,此时Xor清为0 37 } 38 } 39 40 void update(char op,int L,int R,int l,int r,int rt) 41 { 42 if (L<=l && r<=R) 43 { 44 if (op==‘U‘) 45 { 46 cover[rt]=1; 47 Xor[rt]=0; 48 } 49 else if (op==‘D‘) 50 { 51 cover[rt]=0; 52 Xor[rt]=0; 53 } 54 else if (op==‘S‘||op==‘C‘) 55 Fxor(rt); 56 return; 57 } 58 pushdown(rt); 59 int m=(l+r)>>1; 60 if (m>=L) update(op,L,R,lson); 61 else if (op==‘C‘||op==‘I‘) cover[rt<<1]=Xor[rt<<1]=0; 62 if (m+1<=R) update(op,L,R,rson); 63 else if (op==‘C‘||op==‘I‘) cover[rt<<1|1]=Xor[rt<<1|1]=0; 64 } 65 66 void query(int l,int r,int rt) 67 { 68 if (cover[rt]==1) 69 { 70 for (int i=l;i<=r;i++) hash[i]=1; 71 return; 72 }else if (cover[rt]==0) return;//全部覆盖为0的时候直接退出 73 if (l==r) return;//说明已经走到了叶子节点 74 pushdown(rt);//凡是接下来要对孩子进行操作的,均要延迟更新 75 int m=(l+r)>>1; 76 query(lson); 77 query(rson); 78 } 79 80 void init() 81 { 82 char op,lo,ro; 83 int l,r; 84 Xor[1]=cover[1]=0; 85 while (scanf("%c %c%d,%d%c",&op,&lo,&l,&r,&ro)!=EOF) 86 { 87 l<<=1; 88 r<<=1; 89 if (lo==‘(‘) l++; 90 if (ro==‘)‘) r--; 91 if (l>r) 92 { 93 if (op==‘C‘ || op==‘I‘) cover[1]=Xor[1]=0; 94 } 95 else update(op,l,r,0,MAXN,1); 96 getchar(); 97 } 98 } 99 100 void getans() 101 { 102 memset(hash,0,sizeof(hash)); 103 query(0,MAXN,1); 104 int flag=0,s=-1,e=-1; 105 for (int i=0;i<=MAXN;i++) 106 { 107 if (hash[i]==0 && s!=-1) 108 { 109 e=i-1; 110 if (flag) cout<<‘ ‘; 111 flag=1; 112 printf("%c%d,%d%c", s&1?‘(‘:‘[‘, s>>1 , (e+1)>>1 , e&1?‘)‘:‘]‘); 113 s=e=-1; 114 } 115 else 116 if (hash[i]==1 && s==-1) 117 s=i; 118 } 119 if (!flag) cout<<"empty set"<<endl; 120 } 121 122 int main() 123 { 124 //freopen("POJ3225.in","r",stdin); 125 init(); 126 getans(); 127 return 0; 128 }
【线段树】POJ3225-Help with Intervals
标签:
原文地址:http://www.cnblogs.com/iiyiyi/p/5138847.html