Time Limit: 1000MS | Memory Limit: 65536K | |
Total Submissions: 53312 | Accepted: 16050 |
Description
Chosen Problem Solving and Program design as an optional course, you are required to solve all kinds of problems. Here, we get a new problem.
There is a very long board with length L centimeter, L is a positive integer, so we can evenly divide the board into L segments, and they are labeled by 1, 2, ... L from left to right, each is 1 centimeter long. Now we have to color the board - one segment with only one color. We can do following two operations on the board:
1. "C A B C" Color the board from segment A to segment B with color C.
2. "P A B" Output the number of different colors painted between segment A and segment B (including).
In our daily life, we have very few words to describe a color (red, green, blue, yellow…), so you may assume that the total number of different colors T is very small. To make it simple, we express the names of colors as color 1, color 2, ... color T. At the beginning, the board was painted in color 1. Now the rest of problem is left to your.
There is a very long board with length L centimeter, L is a positive integer, so we can evenly divide the board into L segments, and they are labeled by 1, 2, ... L from left to right, each is 1 centimeter long. Now we have to color the board - one segment with only one color. We can do following two operations on the board:
1. "C A B C" Color the board from segment A to segment B with color C.
2. "P A B" Output the number of different colors painted between segment A and segment B (including).
In our daily life, we have very few words to describe a color (red, green, blue, yellow…), so you may assume that the total number of different colors T is very small. To make it simple, we express the names of colors as color 1, color 2, ... color T. At the beginning, the board was painted in color 1. Now the rest of problem is left to your.
Input
First line of input contains L (1 <= L <= 100000), T (1 <= T <= 30) and O (1 <= O <= 100000). Here O denotes the number of operations. Following O lines, each contains "C A B C" or "P A B" (here A, B, C are integers, and A may be larger than B) as an operation defined previously.
Output
Ouput results of the output operation in order, each line contains a number.
Sample Input
2 2 4 C 1 1 2 P 1 2 C 2 2 2 P 1 2
Sample Output
2 1
题意就是区间染色,然后查询区间颜色数量,不能直接线段树上更新值,会被覆盖掉,所以要用二进制状态压缩一下,学到了小技巧,用二进制进行状态压缩。
有关位运算的老是记不住,笨死了。。。
贴一下大佬的有关位运算的:
位运算总结(按位与,或,异或)
还有一篇有关二进制状态压缩的:
状态压缩 位运算
本篇博客完全就是为了备忘才水的。。。
我写的时候,初始化写挫了,查询的时候,ret应该初始化为0,我写的1。。。
运算规则:0|0=0; 0|1=1; 1|0=1; 1|1=1;
即 :参加运算的两个对象只要有一个为1,其值为1。
代码:
1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<algorithm> 5 #include<bitset> 6 #include<cassert> 7 #include<cctype> 8 #include<cmath> 9 #include<cstdlib> 10 #include<ctime> 11 #include<deque> 12 #include<iomanip> 13 #include<list> 14 #include<map> 15 #include<queue> 16 #include<set> 17 #include<stack> 18 #include<vector> 19 using namespace std; 20 typedef long long ll; 21 typedef long double ld; 22 typedef pair<int,int> pii; 23 24 const double PI=acos(-1.0); 25 const double eps=1e-6; 26 const ll mod=1e9+7; 27 const int inf=0x3f3f3f3f; 28 const int maxn=1e5+10; 29 const int maxm=100+10; 30 #define ios ios::sync_with_stdio(false);cin.tie(0);cout.tie(0); 31 #define lson l,m,rt<<1 32 #define rson m+1,r,rt<<1|1 33 34 int tree[maxn<<2],lazy[maxn<<2]; 35 36 void pushup(int rt) 37 { 38 tree[rt]=tree[rt<<1]|tree[rt<<1|1];//颜色汇总 39 } 40 41 void pushdown(int rt) 42 { 43 if(lazy[rt]){ 44 lazy[rt<<1]=lazy[rt<<1|1]=lazy[rt]; 45 tree[rt<<1]=tree[rt<<1|1]=lazy[rt]; 46 lazy[rt]=0; 47 } 48 } 49 50 void build(int l,int r,int rt) 51 { 52 lazy[rt]=0; 53 tree[rt]=1; 54 if(l==r){ 55 return ; 56 } 57 58 int m=(l+r)>>1; 59 build(lson); 60 build(rson); 61 pushup(rt); 62 } 63 64 void update(int L,int R,int c,int l,int r,int rt) 65 { 66 if(r<L||l>R) return ; 67 if(L<=l&&r<=R){ 68 lazy[rt]=1<<(c-1);//二进制状态压缩保存颜色 69 tree[rt]=1<<(c-1); 70 return ; 71 } 72 73 pushdown(rt); 74 int m=(l+r)>>1; 75 if(L<=m) update(L,R,c,lson); 76 if(R> m) update(L,R,c,rson); 77 pushup(rt); 78 } 79 80 int query(int L,int R,int l,int r,int rt) 81 { 82 if(r<L||l>R) return 0; 83 if(L<=l&&r<=R){ 84 return tree[rt]; 85 } 86 87 pushdown(rt); 88 int m=(l+r)>>1; 89 int ret=0; 90 if(L<=m) ret|=query(L,R,lson); 91 if(R> m) ret|=query(L,R,rson); 92 return ret; 93 } 94 95 int main() 96 { 97 ios; 98 int n,m,q; 99 cin>>n>>m>>q; 100 build(1,n,1); 101 while(q--){ 102 char op[2]; 103 int l,r,color; 104 cin>>op; 105 if(op[0]=='C'){ 106 cin>>l>>r>>color; 107 if(l>r) swap(l,r); 108 update(l,r,color,1,n,1); 109 } 110 else{ 111 cin>>l>>r; 112 if(l>r) swap(l,r); 113 int cnt=query(l,r,1,n,1); 114 int ans=0; 115 while(cnt){ 116 if(cnt&1) ans++; 117 cnt>>=1; 118 } 119 cout<<ans<<endl; 120 } 121 } 122 return 0; 123 }
。。。