Black And White
Time Limit: 9000/3000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 3561 Accepted Submission(s):
1062
Problem Description
There are a bunch of stones on the beach; Stone color
is white or black. Little Sheep has a magic brush, she can change the color of a
continuous stone, black to white, white to black. Little Sheep like black very
much, so she want to know the longest period of consecutive black stones in a
range [i, j].
Input
There are multiple cases, the first line of each case
is an integer n(1<= n <= 10^5), followed by n integer 1 or 0(1 indicates
black stone and 0 indicates white stone), then is an integer M(1<=M<=10^5)
followed by M operations formatted as x i j(x = 0 or 1) , x=1 means change the
color of stones in range[i,j], and x=0 means ask the longest period of
consecutive black stones in range[i,j]
Output
When x=0 output a number means the longest length of
black stones in range [i,j].
Sample Input
4
1 0 1 0
5
0 1 4
1 2 3
0 1 4
1 3 3
0 4 4
Sample Output
1
2
0
Source
1 /** 2 题意:两种操作 3 0 l ,r 查找区间[ L , R ]里最长的连续1的数目。 4 1 l ,r 更新区间[ L , R ]里的数字。0变成1, 1变成0 5 6 思路: 7 由于连续1的存在,我们需要保存lnum, rnum. lmaxn, rmaxn maxn; 8 加上1操作,我们还要有个延迟标记才行。 9 bool setFlag; 10 11 如果就设置这些参数。在更新的时候, 12 我们必须要找到一段连续相等数字的区间,对它进行延迟标记。 13 i f ( f[n].maxn == f[n].len || f[n].maxn == 0 ) 14 15 这样的话,我们有可能更新到叶子节点。这样的时间就多了。 16 其实,我们最期望的就是一旦找到区间[ L ,R ]的时候,就进行延迟 17 标记,然后返回。 18 19 由此,我们还要加上统计0个数的数据。 20 Zlmaxn,Zrmaxn,Zmaxn; 21 1的操作本质上也是 0 和 1的转化,所以交换它们的值就可以了。 22 23 同时,我们需要注意,对于setFlag ,只有奇数次的时候才标记为ture; 24 25 **/ 26 27 #include<iostream> 28 #include<stdio.h> 29 #include<cstring> 30 #include<cstdlib> 31 using namespace std; 32 33 struct node 34 { 35 int l,r,len; 36 int lnum,rnum; 37 int lmaxn,rmaxn,maxn; 38 int Zlmaxn,Zrmaxn,Zmaxn; 39 bool setFlag; 40 }f[100002*4]; 41 int date; 42 43 void up(int n) 44 { 45 f[n].lnum = f[n*2].lnum; 46 f[n].rnum = f[n*2+1].rnum; 47 48 f[n].lmaxn = ( f[n*2].lmaxn==f[n*2].len && f[n*2].rnum==f[n*2+1].lnum ) ? 49 f[n*2].lmaxn+f[n*2+1].lmaxn:f[n*2].lmaxn; 50 f[n].rmaxn = ( f[n*2+1].rmaxn == f[n*2+1].len && f[n*2].rnum == f[n*2+1].lnum) ? 51 f[n*2+1].rmaxn+f[n*2].rmaxn : f[n*2+1].rmaxn; 52 f[n].maxn = max(f[n*2].maxn,f[n*2+1].maxn); 53 if(f[n*2].rnum == 1 && f[n*2+1].lnum == 1) 54 f[n].maxn = max(f[n].maxn,f[n*2].rmaxn+f[n*2+1].lmaxn); 55 56 f[n].Zlmaxn = ( f[n*2].Zlmaxn==f[n*2].len && f[n*2].rnum==f[n*2+1].lnum ) ? 57 f[n*2].Zlmaxn+f[n*2+1].Zlmaxn:f[n*2].Zlmaxn; 58 f[n].Zrmaxn = ( f[n*2+1].Zrmaxn == f[n*2+1].len && f[n*2].rnum == f[n*2+1].lnum) ? 59 f[n*2+1].Zrmaxn+f[n*2].Zrmaxn : f[n*2+1].Zrmaxn; 60 f[n].Zmaxn = max(f[n*2].Zmaxn,f[n*2+1].Zmaxn); 61 if(f[n*2].rnum == 0 && f[n*2+1].lnum == 0) 62 f[n].Zmaxn = max(f[n].Zmaxn,f[n*2].Zrmaxn+f[n*2+1].Zlmaxn); 63 } 64 void build(int l,int r,int n) 65 { 66 int mid=(l+r)/2; 67 f[n].l = l; 68 f[n].r = r; 69 f[n].len = f[n].r-f[n].l+1; 70 f[n].setFlag = false; 71 f[n].lnum=f[n].rnum=0; 72 f[n].lmaxn=f[n].rmaxn=f[n].maxn=0; 73 f[n].Zlmaxn=f[n].Zrmaxn=f[n].Zmaxn=0; 74 if(l==r) 75 { 76 scanf("%d",&date); 77 f[n].lnum=f[n].rnum=date; 78 f[n].lmaxn=f[n].rmaxn=f[n].maxn=date; 79 f[n].Zlmaxn=f[n].Zrmaxn=f[n].Zmaxn=(date^1); 80 return; 81 } 82 build(l,mid,n*2); 83 build(mid+1,r,n*2+1); 84 up(n); 85 } 86 87 void down(int n) 88 { 89 f[n*2].setFlag = f[n*2].setFlag^1; 90 /**传递的是奇数次,偶数次就抵消了,不需要向下更新**/ 91 swap(f[n*2].lmaxn,f[n*2].Zlmaxn); 92 swap(f[n*2].rmaxn,f[n*2].Zrmaxn); 93 swap(f[n*2].maxn,f[n*2].Zmaxn); 94 f[n*2].lnum = (f[n*2].lnum^1); 95 f[n*2].rnum = (f[n*2].rnum^1); 96 97 f[n*2+1].setFlag = f[n*2+1].setFlag^1; 98 /**传递的是奇数次,偶数次就抵消了,不需要向下更新**/ 99 swap(f[n*2+1].lmaxn,f[n*2+1].Zlmaxn); 100 swap(f[n*2+1].rmaxn,f[n*2+1].Zrmaxn); 101 swap(f[n*2+1].maxn,f[n*2+1].Zmaxn); 102 f[n*2+1].lnum=(f[n*2+1].lnum^1); 103 f[n*2+1].rnum=(f[n*2+1].rnum^1); 104 105 f[n].setFlag = false; 106 } 107 void update(int l,int r,int n) 108 { 109 int mid=(f[n].l + f[n].r)/2; 110 if(f[n].l == l && f[n].r == r) 111 { 112 f[n].setFlag = (f[n].setFlag^1); 113 /**传递的是奇数次,偶数次就抵消了,不需要向下更新**/ 114 f[n].lnum=(f[n].lnum^1); 115 f[n].rnum=(f[n].rnum^1); 116 swap(f[n].lmaxn,f[n].Zlmaxn); 117 swap(f[n].rmaxn,f[n].Zrmaxn); 118 swap(f[n].maxn,f[n].Zmaxn); 119 return ; 120 } 121 if(f[n].setFlag==true) down(n); 122 if(mid>=r) update(l,r,n*2); 123 else if(mid<l) update(l,r,n*2+1); 124 else 125 { 126 update(l,mid,n*2); 127 update(mid+1,r,n*2+1); 128 } 129 up(n); 130 } 131 132 int query(int l,int r,int n) 133 { 134 int mid=(f[n].l + f[n].r)/2; 135 if(f[n].l == l && f[n].r==r) 136 { 137 return f[n].maxn; 138 } 139 if(f[n].setFlag==true) down(n); 140 if(mid>=r) return query(l,r,n*2); 141 else if(mid<l) return query(l,r,n*2+1); 142 else 143 { 144 int lmaxn = query(l,mid,n*2); 145 int rmaxn = query(mid+1,r,n*2+1); 146 int maxn = max(lmaxn,rmaxn); 147 if(f[n*2].rnum==1 && f[n*2+1].lnum ==1) 148 maxn = max( maxn,min(mid-l+1,f[n*2].rmaxn)+min(r-mid,f[n*2+1].lmaxn) ); 149 return maxn; 150 } 151 } 152 153 int main() 154 { 155 int n,m,l,r,size1; 156 while(scanf("%d",&n)>0) 157 { 158 build(1,n,1); 159 scanf("%d",&m); 160 while(m--) 161 { 162 scanf("%d%d%d",&size1,&l,&r); 163 if(size1==1) 164 update(l,r,1); 165 else if(size1==0) 166 printf("%d\n",query(l,r,1)); 167 } 168 } 169 return 0; 170 }