segment_tree/
propagating.rs1use std::mem;
2use std::default::Default;
3
4use crate::ops::{Commutative, Identity};
5
6pub struct PointSegment<N, O> where O: Commutative<N> + Identity<N> {
42 buf: Vec<N>,
43 n: usize,
44 op: O
45}
46
47impl<N, O: Commutative<N> + Identity<N>> PointSegment<N, O> {
48 pub fn build(mut buf: Vec<N>, op: O) -> PointSegment<N, O> {
52 let n = buf.len();
53 buf.reserve_exact(n);
54 for i in 0..n {
55 let val = mem::replace(&mut buf[i], op.identity());
56 buf.push(val);
57 }
58 PointSegment { buf: buf, n: n, op: op }
59 }
60 pub fn build_slice(buf: &[N], op: O) -> PointSegment<N, O> where N: Clone {
63 PointSegment::build_iter(buf.iter().cloned(), op)
64 }
65 pub fn build_iter<I: ExactSizeIterator<Item=N>>(iter: I, op: O) -> PointSegment<N, O> {
68 let n = iter.len();
69 let mut buf = Vec::with_capacity(2*n);
70 for _ in 0..n { buf.push(op.identity()); }
71 buf.extend(iter);
72 PointSegment {
73 buf: buf,
74 n: n, op: op
75 }
76 }
77 pub fn query(&self, mut p: usize) -> N {
80 p += self.n;
81 let mut res = self.op.identity();
82 while p > 0 {
83 res = self.op.combine_left(res, &self.buf[p]);
84 p >>= 1;
85 }
86 res
87 }
88 pub fn modify(&mut self, mut l: usize, mut r: usize, delta: N) {
91 l += self.n; r += self.n;
92 while l < r {
93 if l&1 == 1 {
94 self.op.combine_mut(&mut self.buf[l], &delta);
95 l += 1;
96 }
97 if r&1 == 1 {
98 r -= 1;
99 self.op.combine_mut(&mut self.buf[r], &delta);
100 }
101 l >>= 1; r >>= 1;
102 }
103 }
104 pub fn propogate(&mut self) -> &mut [N] {
109 for i in 1..self.n {
110 let prev = mem::replace(&mut self.buf[i], self.op.identity());
111 self.op.combine_mut(&mut self.buf[i<<1], &prev);
112 self.op.combine_mut(&mut self.buf[i<<1|1], &prev);
113 }
114 &mut self.buf[self.n..]
115 }
116 #[inline(always)]
119 pub fn len(&self) -> usize {
120 self.n
121 }
122}
123
124impl<N: Clone, O: Identity<N> + Commutative<N> + Clone> Clone for PointSegment<N, O> {
125 #[inline]
126 fn clone(&self) -> PointSegment<N, O> {
127 PointSegment {
128 buf: self.buf.clone(), n: self.n, op: self.op.clone()
129 }
130 }
131}
132impl<N, O: Identity<N> + Commutative<N> + Default> Default for PointSegment<N, O> {
133 #[inline]
134 fn default() -> PointSegment<N, O> {
135 PointSegment { buf: Vec::new(), n: 0, op: Default::default() }
136 }
137}
138
139#[cfg(test)]
140mod tests {
141 use crate::propagating::*;
142 use crate::ops::*;
143 use rand::prelude::*;
144 use rand::distributions::Standard;
145 use std::num::Wrapping;
146
147 #[test]
148 fn test() {
149 let mut rng = thread_rng();
150 for i in 1..130 {
151 let mut buf: Vec<Wrapping<i32>> = rng.sample_iter(&Standard)
152 .map(|n| Wrapping(n)).take(i).collect();
153 let mut tree = match i%3 {
154 0 => PointSegment::build_slice(&buf[..], Add),
155 1 => PointSegment::build_iter(buf.iter().cloned(), Add),
156 2 => PointSegment::build(buf.clone(), Add),
157 _ => unreachable!()
158 };
159 let tests: Vec<(usize, usize, i32)> = rng.sample_iter(&Standard)
160 .take(10).collect();
161 for (n, m, v) in tests {
162 let n = n % i;
163 let m = m % i;
164 if n > m { continue; }
165 for index in n..m { buf[index] += Wrapping(v); }
166 tree.modify(n, m, Wrapping(v));
167 for index in 0..i {
168 assert_eq!(buf[index], tree.query(index));
169 }
170 }
171 assert_eq!(&mut buf[..], tree.propogate());
172 }
173 }
174}