[웰노운] Segment Tree
서론
Segment Tree에 대해 알아보자.
본론
사실 이번 포스트는 UCPC 같은 대회에서 내 코드 템플릿을 만든 것이다.
이 구현에서 주의할 점은 다음과 같다.
- 입력 배열은 0-based index를 따른다, 세그트리의 일반적인 구현은 1-based index이므로 주의해야 한다.
- RSQ(구간 합 쿼리)기반으로 작성되었기 때문에 operation에 대해 수정해야한다.
의사 코드
위 내용을 구현한 c++ 코드이다. 구간 합을 업데이트하는 코드 예제이다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
class segTree {
public:
int n;
vector<int> a, seg;
segTree(int x) : n(x), a(n, 0), seg(4 * n) { init(1, 1, n); }
segTree(vector<int> v) : n(v.size()), a(v), seg(4 * n) { init(1, 1, n); }
int init(int node, int l, int r) {
if (l == r) return seg[node] = a[l - 1];
int mid = (l + r) / 2;
return seg[node] = init(node * 2, l, mid) + init(node * 2 + 1, mid + 1, r);
}
void update(int node, int l, int r, int idx, int k) {
if (idx < l || r < idx) return;
if (l == idx && r == idx) {
seg[node] = a[idx - 1] = k;
return;
}
int mid = (l + r) / 2;
update(node * 2, l, mid, idx, k);
update(node * 2 + 1, mid + 1, r, idx, k);
seg[node] = seg[node * 2] + seg[node * 2 + 1];
}
int query(int node, int l, int r, int ql, int qr) {
if (qr < l || r < ql) return 0;
if (ql <= l && r <= qr) return seg[node];
int mid = (l + r) / 2;
return query(node * 2, l, mid, ql, qr) + query(node * 2 + 1, mid + 1, r, ql, qr);
}
};
이 기사는 저작권자의 CC BY 4.0 라이센스를 따릅니다.