1use std::ops::Range;
12
13pub struct RankIndexNlC(Vec<usize>);
14
15impl RankIndexNlC {
16 pub fn new(a: &[bool]) -> Self {
17 let n = a.len();
18 let mut res = vec![0; n];
19 let mut count = 0;
20 for i in 0..n {
21 if a[i] {
22 count += 1;
23 }
24 res[i] = count;
25 }
26 Self(res)
27 }
28 pub fn rank<const X: bool>(&self, i: usize) -> usize {
29 if X { self.0[i] } else { i + 1 - self.0[i] }
30 }
31}
32
33pub struct SelectIndexNlC(Vec<usize>);
34
35impl SelectIndexNlC {
36 pub fn new<const X: bool>(a: &[bool]) -> Self {
37 let n = a.len();
38 let mut res = vec![0; n];
39 let mut count = 0;
40 for i in 0..n {
41 if a[i] == X {
42 res[count] = i;
43 count += 1;
44 }
45 }
46 Self(res)
47 }
48 pub fn select(&self, i: usize) -> usize { self.0[i] }
49}
50
51pub fn select_word<const X: bool>(mut w: u64, mut i: u32) -> u32 {
52 if !X {
53 w = !w;
54 }
55 let mut res = 0;
56 for lg2 in (0..6).rev() {
57 let len = 1 << lg2;
58 let mask = !(!0 << len);
59 let count = (w & mask).count_ones();
60 if count <= i {
61 w >>= len;
62 i -= count;
63 res += len;
64 }
65 }
66 res
67}
68
69pub struct Rs01DictNlC {
70 rank_index: RankIndexNlC,
71 select1_index: SelectIndexNlC,
72 select0_index: SelectIndexNlC,
73}
74
75impl Rs01DictNlC {
76 pub fn new(a: &[bool]) -> Self {
77 Self {
78 rank_index: RankIndexNlC::new(a),
79 select1_index: SelectIndexNlC::new::<true>(a),
80 select0_index: SelectIndexNlC::new::<false>(a),
81 }
82 }
83 fn rank<const X: bool>(&self, i: usize) -> usize {
84 self.rank_index.rank::<X>(i)
85 }
86 fn select<const X: bool>(&self, i: usize) -> usize {
87 if X {
88 self.select1_index.select(i)
89 } else {
90 self.select0_index.select(i)
91 }
92 }
93
94 pub fn rank1(&self, i: usize) -> usize { self.rank::<true>(i) }
95 pub fn rank0(&self, i: usize) -> usize { self.rank::<false>(i) }
96 pub fn select1(&self, i: usize) -> usize { self.select::<true>(i) }
97 pub fn select0(&self, i: usize) -> usize { self.select::<false>(i) }
98}
99
100struct RankIndexNLl {
101 block: Vec<usize>,
102 buf: Vec<u64>,
103}
104
105const W: usize = u64::BITS as usize;
106
107impl RankIndexNLl {
108 pub fn new(a: &[bool]) -> Self {
109 let len = a.len();
110 let n = (len + W - 1) / W;
111 let mut buf = vec![0_u64; n + 1];
112 for i in 0..len {
113 if a[i] {
114 buf[i / W] |= 1 << (i % W);
115 }
116 }
117 let block: Vec<_> = buf
118 .iter()
119 .map(|x| x.count_ones() as usize)
120 .scan(0, |acc, x| Some(std::mem::replace(acc, *acc + x)))
121 .collect();
122 Self { block, buf }
123 }
124 pub fn rank<const X: bool>(&self, i: usize) -> usize {
125 let i = i + 1;
126 let large = i / W;
127 let small = i % W;
128 let mini = self.buf[large] & !(!0 << small);
129 let count1 = self.block[large] + mini.count_ones() as usize;
130 if X { count1 } else { i - count1 }
131 }
132 pub fn rank_bisect<const X: bool>(
133 &self,
134 i: usize,
135 range: Range<usize>,
136 ) -> usize {
137 let mut lo = range.start / W;
138 let mut hi = (range.end + W - 1) / W;
139 while hi - lo > 1 {
140 let mid = lo + (hi - lo) / 2;
141 let count1 = self.block[mid];
142 let count = if X { count1 } else { mid * W - count1 };
143 *(if count <= i { &mut lo } else { &mut hi }) = mid;
144 }
145 let count1 = self.block[lo];
146 let count = if X { count1 } else { lo * W - count1 };
147 lo * W + select_word::<X>(self.buf[lo], (i - count) as _) as usize
148 }
149}
150
151struct SelectIndexNLl<const POPCNT: usize, const SPARSE_LEN: usize> {
152 inner: Vec<SelectIndexNLlInner>,
153}
154
155impl<const POPCNT: usize, const SPARSE_LEN: usize>
156 SelectIndexNLl<POPCNT, SPARSE_LEN>
157{
158 pub fn new<const X: bool>(a: &[bool]) -> Self {
159 let n = a.len();
160 let mut cur = vec![];
161 let mut res = vec![];
162 let mut start = 0;
163 for i in 0..n {
164 if a[i] == X {
165 cur.push(i);
166 }
167 if cur.len() >= POPCNT || i == n - 1 {
168 let tmp = std::mem::take(&mut cur);
169 if tmp.len() >= SPARSE_LEN {
170 res.push(SelectIndexNLlInner::Sparse(tmp));
171 } else {
172 res.push(SelectIndexNLlInner::Dense(start..i + 1));
173 }
174 start = i + 1;
175 }
176 }
177 Self { inner: res }
178 }
179
180 pub fn select<const X: bool>(&self, i: usize, r: &RankIndexNLl) -> usize {
181 self.inner[i / POPCNT].select::<X>(i, i % POPCNT, r)
182 }
183}
184
185enum SelectIndexNLlInner {
186 Sparse(Vec<usize>),
187 Dense(Range<usize>),
188}
189
190impl SelectIndexNLlInner {
191 fn select<const X: bool>(
192 &self,
193 i: usize,
194 i_rem: usize,
195 r: &RankIndexNLl,
196 ) -> usize {
197 match self {
198 Self::Sparse(pos) => pos[i_rem],
199 Self::Dense(Range { start, end }) => {
200 let lo = *start;
201 let hi = *end;
202 if r.rank::<X>(lo) > i {
203 return lo;
204 }
205 r.rank_bisect::<X>(i, lo..hi)
206 }
207 }
208 }
209}
210
211const POPCNT: usize = 64; const SPARSE_LEN: usize = 4096; pub type Rs01DictNLl = Rs01DictNLlParam<POPCNT, SPARSE_LEN>;
215
216pub struct Rs01DictNLlParam<const POPCNT: usize, const SPARSE_LEN: usize> {
217 rank_index: RankIndexNLl,
218 select1_index: SelectIndexNLl<POPCNT, SPARSE_LEN>,
219 select0_index: SelectIndexNLl<POPCNT, SPARSE_LEN>,
220}
221
222impl<const POPCNT: usize, const SPARSE_LEN: usize>
223 Rs01DictNLlParam<POPCNT, SPARSE_LEN>
224{
225 pub fn new(a: &[bool]) -> Self {
226 Self {
227 rank_index: RankIndexNLl::new(a),
228 select1_index: SelectIndexNLl::new::<true>(a),
229 select0_index: SelectIndexNLl::new::<false>(a),
230 }
231 }
232 fn rank<const X: bool>(&self, i: usize) -> usize {
233 self.rank_index.rank::<X>(i)
234 }
235 fn select<const X: bool>(&self, i: usize) -> usize {
236 if X {
237 self.select1_index.select::<X>(i, &self.rank_index)
238 } else {
239 self.select0_index.select::<false>(i, &self.rank_index)
240 }
241 }
242
243 pub fn rank1(&self, i: usize) -> usize { self.rank::<true>(i) }
244 pub fn rank0(&self, i: usize) -> usize { self.rank::<false>(i) }
245 pub fn select1(&self, i: usize) -> usize { self.select::<true>(i) }
246 pub fn select0(&self, i: usize) -> usize { self.select::<false>(i) }
247}
248
249#[test]
250fn sanity_check() {
251 let w = 0b_1100_1011_0010_1101_1001_1000_0001_0100_1111_1110_0000_0011_0111_0101_1010_0110_u64;
254 let mut wi = w;
255 for i in 0..32 {
256 let expected = wi.trailing_zeros();
257 let actual = select_word::<true>(w, i);
258 assert_eq!(actual, expected);
259 wi ^= wi & wi.wrapping_neg();
260 }
261}
262
263#[cfg(test)]
264macro_rules! bitvec {
265 ($lit:literal) => {
266 $lit.iter()
267 .filter(|&&b| matches!(b, b'0' | b'1'))
268 .map(|&b| b != b'0')
269 .collect::<Vec<_>>()
270 };
271}
272
273#[test]
274fn sanity_check_rank() {
275 let a = bitvec!(b"000 010 110 000; 111 001 000 011; 000 000 010 010");
276 let rs = Rs01DictNLlParam::<100, 100>::new(&a);
277 let expected1 = [
278 0, 0, 0, 0, 1, 1, 2, 3, 3, 3, 3, 3, 4, 5, 6, 6, 6, 7, 7, 7, 7, 7, 8, 9,
279 9, 9, 9, 9, 9, 9, 9, 10, 10, 10, 11, 11,
280 ];
281 let actual1: Vec<_> = (0..a.len()).map(|i| rs.rank1(i)).collect();
282 assert_eq!(actual1, expected1);
283
284 let expected0 = [
285 1, 2, 3, 4, 4, 5, 5, 5, 6, 7, 8, 9, 9, 9, 9, 10, 11, 11, 12, 13, 14,
286 15, 15, 15, 16, 17, 18, 19, 20, 21, 22, 22, 23, 24, 24, 25,
287 ];
288 let actual0: Vec<_> = (0..a.len()).map(|i| rs.rank0(i)).collect();
289 assert_eq!(actual0, expected0);
290}
291
292#[test]
293fn sanity_check_select_dense() {
294 let a = bitvec!(b"000 010 110; 000 111 001; 000 011 000");
295 let ones = a.iter().filter(|&&x| x).count();
296 let zeros = a.len() - ones;
297 let rs = Rs01DictNLlParam::<100, 100>::new(&a);
298 let expected1: Vec<_> = (0..a.len()).filter(|&i| a[i]).collect();
299 let expected0: Vec<_> = (0..a.len()).filter(|&i| !a[i]).collect();
300 let actual1: Vec<_> = (0..ones).map(|i| rs.select1(i)).collect();
301 let actual0: Vec<_> = (0..zeros).map(|i| rs.select0(i)).collect();
302 assert_eq!(actual1, expected1);
303 assert_eq!(actual0, expected0);
304}
305
306#[test]
307fn sanity_check_select_sparse() {
308 let a = bitvec!(b"001 010 000; 000 000 110");
309 let ones = a.iter().filter(|&&x| x).count();
310 let zeros = a.len() - ones;
311 let rs = Rs01DictNLlParam::<2, 0>::new(&a);
312 let expected1: Vec<_> = (0..a.len()).filter(|&i| a[i]).collect();
313 let expected0: Vec<_> = (0..a.len()).filter(|&i| !a[i]).collect();
314 let actual1: Vec<_> = (0..ones).map(|i| rs.select1(i)).collect();
315 let actual0: Vec<_> = (0..zeros).map(|i| rs.select0(i)).collect();
316 assert_eq!(actual1, expected1);
317 assert_eq!(actual0, expected0);
318}