Note:
The interval size is 100000000. Then, each time you query how many values in a interval are not marked and all unmarked values in the interval are marked.
Query times: 100000
Analysis:
This question gives me the first feeling that the line segment tree cannot be opened if the line segment tree is 10 ^ 7.
And then the query set once again exert its infinite power
For the interval of each query
Point all the values to the farthest value he can point.
The total number of queries can be controlled within 10 ^ 7.
Perfect solution
A little abstract
Simulate it with code and you will find out how witty this method is.
I'm going to use a line segment tree
Code:
1 #include <iostream> 2 #include <cstdio> 3 #include <cstring> 4 using namespace std; 5 6 const int maxn = 10000005; 7 8 int fa[maxn]; 9 10 int find(int x) {11 if(x == fa[x]) return x;12 return fa[x] = find(fa[x]);13 }14 15 int main() {16 int t;17 int n, m;18 int a, b;19 scanf("%d",&t);20 while(t--) {21 scanf("%d %d",&n, &m);22 for(int i = 0; i <= n + 3; i++) {23 fa[i] = i;24 }25 for(int i = 1; i <= m; i++) {26 scanf("%d %d",&a, &b);27 int p = find(a);28 int cnt = 0;29 while(p <= b) {30 cnt ++;31 fa[find(p)] = find(p + 1);32 p = find(p + 1);33 }34 printf("%d\n",cnt);35 }36 }37 return 0;38 }
View code
1 #include <iostream> 2 #include <cstdio> 3 #include <cstring> 4 using namespace std; 5 6 const int maxn = 1000005; 7 8 struct Node { 9 int left, right;10 int tot; 11 int mark;12 }tree[maxn << 2];13 14 int creat(int root, int left, int right) {15 tree[root].mark = 0;16 tree[root].left = left;17 tree[root].right = right;18 if(left == right) return tree[root].total = 1;19 int a, b, mid = (left + right) >> 1;20 a = creat(root << 1, left, mid);21 b = creat(root << 1 | 1, mid + 1, right);22 return tree[root].tot = a + b;23 }24 25 void update_mark(int root) {26 if(tree[root].mark) {27 tree[root].tot = tree[root].mark ;28 if(tree[root].left != tree[root].right) {29 tree[root<<1].left = tree[root<<1|1].right = tree[root].mark;30 }31 tree[root].mark = 0;32 }33 }34 35 int update(int root, int left, int right) {36 update_mark(root);37 38 if(tree[root].left > right || tree[root].right < left) {39 return tree[root].tot;40 }41 42 if(left <= tree[root].left && tree[root].right <= right) {43 tree[root].mark = 1;44 return tree[root].tot = 0;45 }46 47 int a, b;48 49 a = update(root << 1, left, right);50 b = update(root << 1 | 1, left, right);51 return tree[root].tot = a + b;52 }53 54 55 int cal(int root, int left, int right) {56 update_mark(root);57 58 if(tree[root].left > right || tree[root].right < left) {59 return 0;60 }61 62 if(tree[root].left >= left && tree[root].right <= right) {63 return tree[root].tot;64 }65 66 int a, b;67 68 a = cal(root << 1, a, b);69 b = cal(root << 1 | 1, a, b);70 return a + b;71 }72 73 int main() {74 int t;75 int n, m;76 int a, b;77 78 scanf("%d",&t);79 while(t--) {80 scanf("%d %d",&n, &m);81 creat(1, 1, n);82 for(int i = 1; i <= m; i++) {83 scanf("%d %d",&a, &b);84 printf("%d\n", cal(1, a, b) );85 update(1, a, b);86 }87 }88 return 0;89 }
View code
Hlgchocolate auction [query set]