The Segment Tree is a data structure that maintains an array of numbers by maintaining , where
which costs a space of .
Proof
Modify
Modify updates to in time and space.
Algorithm
Updating the maintained segments containing the given element yields an algorithm that solves the problem in time and space.
void modify(int i, int x) {
y_combinator([&](auto &&self, int o, int s, int t) -> void {
if (s + 1 == t) {
sum[o] = x;
return;
}
int mid = std::midpoint(s, t);
if (i < mid) {
self(o << 1, s, mid);
} else {
self(o << 1 | 1, mid, t);
}
sum[o] = sum[o << 1] + sum[o << 1 | 1];
})(1, 0, n);
}Proof
It is easy to prove that exactly segment is visited in each layer.
Range Sum Query
Range Sum Query computes in time and space.
Algorithm
Decomposing the query interval into maintained segments yields an algorithm that solves the problem in time and space.
int range_sum_query(int l, int r) {
return y_combinator([&](auto &&self, int o, int s, int t) -> int {
if (s >= r || t <= l) {
return 0;
}
if (l <= s && t <= r) {
return sum[o];
}
int mid = std::midpoint(s, t);
return self(o << 1, s, mid) + self(o << 1 | 1, mid, t);
})(1, 0, n);
}Proof
It is easy to prove that at most segments are visited in each layer.