LinkLinkLink
DescriptionDescriptionDescription
There is a line segment of length n in the plane (also called a line segment). The following two operations can be performed:
1 x y adds another line segment from X to y
2 x Query How many line segments are there from X to x+1
InputInputInput
First line input n, m
Line 2~m+1, 3 numbers per row
OutputOutputOutput
For each query operation, the number of output lines
SampleSampleSample InputInputInput
7 5 2 3 1 2 5 2 4 1 4 5 2 4
SampleSampleSample OutputOutputOutput
1 2 3
In fact, this example is false. (There is no correct example yet)
HintHintHint
[Data Scale] 100% satisfies 1 < n < 100000, 1 < x < y < n
TrainTrainTrain ofofof ThoughtThoughtThought
Just count how many line segments cover each interval.
CodeCodeCode
#include<iostream> #include<cstdio> using namespace std; int ans, n, m; struct Tree { int l, r, num; }tree[400005]; void Build(int x, int L, int R) { tree[x].l = L, tree[x].r = R; if (L + 1 >= R) return; int mid = (L + R) >> 1; Build(x * 2, L, mid); Build(x * 2 + 1, mid, R); }//Don't talk too much about building a tree. void Ins(int x, int L, int R) { if (tree[x].l == L && tree[x].r == R) { tree[x].num ++; return ; }//Record how many line segments exactly cover the current interval int mid = (tree[x].l + tree[x].r) >> 1; if (R <= mid) Ins(x * 2, L, R); else if (L >= mid) Ins(x * 2 + 1, L, R); else { Ins(x * 2, L, mid); Ins(x * 2 + 1, mid, R); } } int Print(int x) { while (x > 0) { ans += tree[x].num; x >>= 1; } return ans; }//Statistical answers int Count(int x, int L, int R) { int mid = (tree[x].l + tree[x].r) >> 1; if (tree[x].l == L && tree[x].r == R) return Print(x);//Find out the location of the interval. if (R <= mid) Count(x * 2, L, R); else if (L >= mid) Count(x * 2 + 1, L, R); else { Count(x * 2, L, mid); Count(x * 2 + 1, mid, R); } } int main() { int x, y; scanf("%d%d", &n, &m); Build(1, 1, n); for (int i = 1; i <= m; ++i) { scanf("%d%d", &x, &y); Ins(1, x, y); } scanf("%d%d", &x, &y); printf("%d", Count(1, x, y)); return 0; }