1use std::{error::Error, fmt};
2
3#[rustfmt::skip]
4const MAGIC: [(i32, i32, i32); 64] = [
5 (-1, -1, 0),
7 (-0b10000000000000000000000000000000, 0, 0),
8 (0b1010101010101010101010101010101, 0b1010101010101010101010101010101, 0),
9 (-0b10000000000000000000000000000000, 0, 1),
10 (0b110011001100110011001100110011, 0b110011001100110011001100110011, 0),
11 (0b101010101010101010101010101010, 0b101010101010101010101010101010, 0),
12 (0b100100100100100100100100100100, 0b100100100100100100100100100100, 0),
13 (-0b10000000000000000000000000000000, 0, 2),
14 (0b11100011100011100011100011100, 0b11100011100011100011100011100, 0),
15 (0b11001100110011001100110011001, 0b11001100110011001100110011001, 0),
16 (0b10111010001011101000101110100, 0b10111010001011101000101110100, 0),
17 (0b10101010101010101010101010101, 0b10101010101010101010101010101, 0),
18 (0b10011101100010011101100010011, 0b10011101100010011101100010011, 0),
19 (0b10010010010010010010010010010, 0b10010010010010010010010010010, 0),
20 (0b10001000100010001000100010001, 0b10001000100010001000100010001, 0),
21 (-0b10000000000000000000000000000000, 0, 3),
22 (0b1111000011110000111100001111, 0b1111000011110000111100001111, 0),
23 (0b1110001110001110001110001110, 0b1110001110001110001110001110, 0),
24 (0b1101011110010100001101011110, 0b1101011110010100001101011110, 0),
25 (0b1111111111111111111111111111000, 0b1111111111111111111111111111000, 0),
26 (0b1100001100001100001100001100, 0b1100001100001100001100001100, 0),
27 (0b1011101000101110100010111010, 0b1011101000101110100010111010, 0),
28 (0b1011001000010110010000101100, 0b1011001000010110010000101100, 0),
29 (0b1010101010101010101010101010, 0b1010101010101010101010101010, 0),
30 (0b1010001111010111000010100011, 0b1010001111010111000010100011, 0),
31 (0b1001110110001001110110001001, 0b1001110110001001110110001001, 0),
32 (0b1001011110110100001001011110, 0b1001011110110100001001011110, 0),
33 (0b1001001001001001001001001001, 0b1001001001001001001001001001, 0),
34 (0b1000110100111101110010110000, 0b1000110100111101110010110000, 0),
35 (0b1000100010001000100010001000, 0b1000100010001000100010001000, 0),
36 (0b1000010000100001000010000100, 0b1000010000100001000010000100, 0),
37 (-0b10000000000000000000000000000000, 0, 4),
38 (0b111110000011111000001111100, 0b111110000011111000001111100, 0),
39 (0b111100001111000011110000111, 0b111100001111000011110000111, 0),
40 (0b111010100000111010100000111, 0b111010100000111010100000111, 0),
41 (0b111000111000111000111000111, 0b111000111000111000111000111, 0),
42 (0b110111010110011111001000101, 0b110111010110011111001000101, 0),
43 (0b110101111001010000110101111, 0b110101111001010000110101111, 0),
44 (0b110100100000110100100000110, 0b110100100000110100100000110, 0),
45 (0b110011001100110011001100110, 0b110011001100110011001100110, 0),
46 (0b110001111100111000001100011, 0b110001111100111000001100011, 0),
47 (0b110000110000110000110000110, 0b110000110000110000110000110, 0),
48 (0b101111101000001011111010000, 0b101111101000001011111010000, 0),
49 (0b101110100010111010001011101, 0b101110100010111010001011101, 0),
50 (0b101101100000101101100000101, 0b101101100000101101100000101, 0),
51 (0b101100100001011001000010110, 0b101100100001011001000010110, 0),
52 (0b101011100100110001000001010, 0b101011100100110001000001010, 0),
53 (0b101010101010101010101010101, 0b101010101010101010101010101, 0),
54 (0b101001110010111100000101001, 0b101001110010111100000101001, 0),
55 (0b101000111101011100001010001, 0b101000111101011100001010001, 0),
56 (0b101000001010000010100000101, 0b101000001010000010100000101, 0),
57 (0b100111011000100111011000100, 0b100111011000100111011000100, 0),
58 (0b100110101001000011100111110, 0b100110101001000011100111110, 0),
59 (0b100101111011010000100101111, 0b100101111011010000100101111, 0),
60 (0b100101001111001000001001010, 0b100101001111001000001001010, 0),
61 (0b100100100100100100100100100, 0b100100100100100100100100100, 0),
62 (0b100011111011100000100011111, 0b100011111011100000100011111, 0),
63 (0b100011010011110111001011000, 0b100011010011110111001011000, 0),
64 (0b100010101101100011110010111, 0b100010101101100011110010111, 0),
65 (0b100010001000100010001000100, 0b100010001000100010001000100, 0),
66 (0b100001100100101110001010011, 0b100001100100101110001010011, 0),
67 (0b100001000010000100001000010, 0b100001000010000100001000010, 0),
68 (0b100000100000100000100000100, 0b100000100000100000100000100, 0),
69 (-0b10000000000000000000000000000000, 0, 5),
70];
71
72#[derive(Clone, Debug, Default)]
74pub struct BitStorage {
75 pub data: Vec<u64>,
76 bits: usize,
77 mask: u64,
78 size: usize,
79 values_per_long: usize,
80 divide_mul: u64,
81 divide_add: u64,
82 divide_shift: i32,
83}
84
85#[derive(Debug)]
86pub enum BitStorageError {
87 InvalidLength { got: usize, expected: usize },
88}
89impl fmt::Display for BitStorageError {
90 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
91 match self {
92 BitStorageError::InvalidLength { got, expected } => write!(
93 f,
94 "Invalid length given for storage, got: {got}, but expected: {expected}",
95 ),
96 }
97 }
98}
99impl Error for BitStorageError {}
100
101impl BitStorage {
102 pub fn new(bits: usize, size: usize, data: Option<Vec<u64>>) -> Result<Self, BitStorageError> {
105 if let Some(data) = &data {
106 if data.is_empty() {
108 return Ok(BitStorage {
109 data: Vec::new(),
110 bits,
111 size,
112 ..Default::default()
113 });
114 }
115 }
116
117 debug_assert!((1..=32).contains(&bits));
118
119 let values_per_long = 64 / bits;
120 let magic_index = values_per_long - 1;
121 let (divide_mul, divide_add, divide_shift) = MAGIC[magic_index];
122 let calculated_length = size.div_ceil(values_per_long);
123
124 let mask = (1 << bits) - 1;
125
126 let using_data = if let Some(data) = data {
127 if data.len() != calculated_length {
128 return Err(BitStorageError::InvalidLength {
129 got: data.len(),
130 expected: calculated_length,
131 });
132 }
133 data
134 } else {
135 vec![0; calculated_length]
136 };
137
138 Ok(BitStorage {
139 data: using_data,
140 bits,
141 mask,
142 size,
143 values_per_long,
144 divide_mul: divide_mul as u32 as u64,
145 divide_add: divide_add as u32 as u64,
146 divide_shift,
147 })
148 }
149
150 pub fn cell_index(&self, index: u64) -> usize {
151 let first = self.divide_mul;
153 let second = self.divide_add;
154
155 (((index * first) + second) >> 32 >> self.divide_shift) as usize
156 }
157
158 pub fn get(&self, index: usize) -> u64 {
165 assert!(
166 index < self.size,
167 "Index {index} out of bounds (must be less than {})",
168 self.size
169 );
170
171 if self.data.is_empty() {
173 return 0;
174 }
175
176 let cell_index = self.cell_index(index as u64);
177 let cell = &self.data[cell_index];
178 let bit_index = (index - cell_index * self.values_per_long) * self.bits;
179 (cell >> bit_index) & self.mask
180 }
181
182 pub fn get_and_set(&mut self, index: usize, value: u64) -> u64 {
183 if self.data.is_empty() {
185 return 0;
186 }
187
188 debug_assert!(index < self.size);
189 debug_assert!(value <= self.mask);
190 let cell_index = self.cell_index(index as u64);
191 let cell = &mut self.data[cell_index];
192 let bit_index = (index - cell_index * self.values_per_long) * self.bits;
193 let old_value = (*cell >> (bit_index as u64)) & self.mask;
194 *cell = (*cell & !(self.mask << bit_index)) | ((value & self.mask) << bit_index);
195 old_value
196 }
197
198 pub fn set(&mut self, index: usize, value: u64) {
199 if self.data.is_empty() {
201 return;
202 }
203
204 debug_assert!(index < self.size);
205 debug_assert!(value <= self.mask);
206 let cell_index = self.cell_index(index as u64);
207 let cell = &mut self.data[cell_index];
208 let bit_index = (index - cell_index * self.values_per_long) * self.bits;
209 *cell = (*cell & !(self.mask << bit_index)) | ((value & self.mask) << bit_index);
210 }
211
212 #[inline]
214 pub fn size(&self) -> usize {
215 self.size
216 }
217
218 pub fn iter(&self) -> BitStorageIter {
219 BitStorageIter {
220 storage: self,
221 index: 0,
222 }
223 }
224}
225
226pub struct BitStorageIter<'a> {
227 storage: &'a BitStorage,
228 index: usize,
229}
230
231impl Iterator for BitStorageIter<'_> {
232 type Item = u64;
233
234 fn next(&mut self) -> Option<Self::Item> {
235 if self.index >= self.storage.size {
236 return None;
237 }
238
239 let value = self.storage.get(self.index);
240 self.index += 1;
241 Some(value)
242 }
243}
244
245#[cfg(test)]
246mod tests {
247 use super::*;
248
249 #[test]
250 fn test_wikivg_example() {
251 let data = [
252 1, 2, 2, 3, 4, 4, 5, 6, 6, 4, 8, 0, 7, 4, 3, 13, 15, 16, 9, 14, 10, 12, 0, 2,
253 ];
254 let compact_data: [u64; 2] = [0x0020863148418841, 0x01018A7260F68C87];
255 let storage = BitStorage::new(5, data.len(), Some(compact_data.to_vec())).unwrap();
256
257 for (i, expected) in data.iter().enumerate() {
258 assert_eq!(storage.get(i), *expected);
259 }
260 }
261}