【POJ2777】Count Color(线段树)
以下是题目大意:
有水平方向上很多块板子拼成的墙,一开始每一块都被涂成了颜色1,有C和P两个操作,代表的意思是:
C X Y Z —— 从X到Y将板子涂成颜色Z
P X Y —— 查询X到Y的板子共有多少种颜色
1 2 2 4 //有2块板子 两2颜色 4个询问 2 C 1 1 2 3 P 1 2 4 C 2 2 2 5 P 1 2
自己AC后上网查阅了许多别人的题解,看很多人用的什么“状态压缩”、“位运算”等等方法。感觉自己不会的知识还有很多。我用的方法是类似于hash的思想,每次将颜色查询时标记,由于这题的数据范围很小,不需要用离散化处理,所以比较好写。下面附上代码。
1 /*********************************************/ 2 /* author: Desgard_Duan */ 3 /* motto : Everything is surprise for you! */ 4 /*********************************************/ 5 6 #include <iostream> 7 #include <cstring> 8 #include <cstdlib> 9 #include <cstdio> 10 #include <cctype> 11 #include <cmath> 12 #include <algorithm> 13 #include <numeric> 14 #include <string> 15 #include <limits.h> 16 #include <vector> 17 #include <set> 18 #include <map> 19 20 using namespace std; 21 22 const int maxn = 100100; 23 int col[maxn << 2], ans = 0; 24 int Hash[50]; 25 26 void pushDown (int rt) { 27 if (col[rt]) { 28 col[rt * 2] = col[rt * 2 + 1] = col[rt]; 29 col[rt] = 0; 30 } 31 } 32 33 void build (int l, int r, int rt) { 34 col[rt] = 1; 35 if (l == r) return ; 36 int m = (l + r) / 2; 37 build (l, m, rt * 2); 38 build (m + 1, r, rt * 2 + 1); 39 } 40 41 void update (int L, int R, int c, int l, int r, int rt) { 42 if (L <= l && r <= R) { 43 col[rt] = c; 44 return ; 45 } 46 pushDown (rt); 47 int m = (l + r) / 2; 48 if (L <= m) update (L, R, c, l, m, rt * 2 ); 49 if (m < R) update (L, R, c, m + 1, r, rt * 2 + 1); 50 } 51 52 void query (int L, int R, int l, int r, int rt) { 53 if (col[rt]) { 54 if (Hash[col[rt]] == 0) { 55 ans ++; 56 Hash[col[rt]] = 1; 57 } 58 return ; 59 } 60 int m = (l + r) / 2; 61 if (m >= L) query (L, R, l, m, rt * 2); 62 if (m < R) query (L, R, m + 1, r, rt * 2 + 1); 63 } 64 65 int main () { 66 int L, T, O, x, y, z; 67 char op[5]; 68 while (~scanf ("%d%d%d", &L, &T, &O)) { 69 memset (col, 1, sizeof (col)); 70 build (1, L, 1); 71 while (O --) { 72 scanf ("%s%d%d", op, &x, &y); 73 if (x > y) swap (x, y); 74 if (op[0] == 'C') { 75 scanf ("%d", &z); 76 update (x, y, z, 1, L, 1); 77 } else { 78 memset (Hash, 0, sizeof (Hash)); 79 ans = 0; 80 query (x, y, 1, L, 1); 81 printf ("%d\n", ans); 82 } 83 } 84 } 85 return 0; 86 }