flat_tree/
lib.rs

1#![forbid(missing_docs)]
2#![cfg_attr(test, deny(warnings))]
3#![doc(test(attr(deny(warnings))))]
4//! # Series of functions to map a binary tree to a list
5//!
6//! You can represent a binary tree in a simple flat list using the following
7//! structure:
8//!
9//! ```text
10//!                                     15
11//!               7                                             23
12//!       3                 11                      19                      27
13//!   1       5        9          13          17          21          25          29
14//! 0   2   4   6   8    10    12    14    16    18    20    22    24    26    28    30...
15//! ```
16//!
17//! Each number represents an **index** in a flat list. So a tree:
18//!
19//! ```text
20//!       A
21//!   B       C
22//! D   E   F   G  ...
23//! ```
24//!
25//! would be represented as a list: `[D B E A F C G]`
26//!
27//! Furthermore, indexes `0`, `2`, `4`, `6` are on **depth** `0`. `1`, `5`, `9` on depth `1`. And so forth.
28//!
29//! ```text
30//! depth = 2  ^        3
31//! depth = 1  |    1       5
32//! depth = 0  |  0   2   4   6  ...
33//! ```
34//!
35//! In some cases it is also useful to calculate an **offset**. Indexes `0`, `1`, `3`, `7` have an offset `0`:
36//!
37//! ```text
38//!                 (7)
39//!        (3)
40//!   (1)       5
41//! (0)   2   4   6      ...
42//! ```
43//!
44//! `2`, `5`, `11`, `23` offset `1`:
45//!
46//! ```text
47//!                  7
48//!        3                  (11)
49//!   1        (5)        9          13
50//! 0   (2)   4   6    8    10    12    14
51//! ```
52//!
53//! This module exposes a series of functions to help you build and maintain
54//! this data structure.
55
56mod iterator;
57
58pub use iterator::Iterator;
59
60/// Returns the flat-tree of the tree node at the specified depth and offset.
61///
62/// ## Examples
63/// ```rust
64/// assert_eq!(flat_tree::index(0, 0), 0);
65/// assert_eq!(flat_tree::index(0, 1), 2);
66/// assert_eq!(flat_tree::index(0, 2), 4);
67/// assert_eq!(flat_tree::index(1, 2), 9);
68/// assert_eq!(flat_tree::index(1, 3), 13);
69/// assert_eq!(flat_tree::index(2, 1), 11);
70/// assert_eq!(flat_tree::index(2, 2), 19);
71/// assert_eq!(flat_tree::index(3, 0), 7);
72/// assert_eq!(flat_tree::index(3, 1), 23);
73/// ```
74#[inline]
75pub const fn index(depth: u64, offset: u64) -> u64 {
76  (offset << (depth + 1)) | ((1 << depth) - 1)
77}
78
79/// Returns the depth of a node.
80///
81/// ## Examples
82/// ```rust
83/// assert_eq!(flat_tree::depth(0), 0);
84/// assert_eq!(flat_tree::depth(1), 1);
85/// assert_eq!(flat_tree::depth(2), 0);
86/// assert_eq!(flat_tree::depth(3), 2);
87/// assert_eq!(flat_tree::depth(4), 0);
88/// ```
89#[inline]
90pub const fn depth(i: u64) -> u64 {
91  // Count trailing `1`s of the binary representation of the number.
92  (!i).trailing_zeros() as u64
93}
94
95/// Returns the offset of a node.
96///
97/// ## Examples
98/// ```rust
99/// assert_eq!(flat_tree::offset(0), 0);
100/// assert_eq!(flat_tree::offset(1), 0);
101/// assert_eq!(flat_tree::offset(2), 1);
102/// assert_eq!(flat_tree::offset(3), 0);
103/// assert_eq!(flat_tree::offset(4), 2);
104/// ```
105#[inline]
106pub fn offset(i: u64) -> u64 {
107  let depth = self::depth(i);
108  if is_even(i) {
109    i / 2
110  } else {
111    i >> (depth + 1)
112  }
113}
114
115/// Returns the parent of a node with a depth.
116///
117/// ## Examples
118/// ```rust
119/// assert_eq!(flat_tree::parent(0), 1);
120/// assert_eq!(flat_tree::parent(1), 3);
121/// assert_eq!(flat_tree::parent(2), 1);
122/// assert_eq!(flat_tree::parent(3), 7);
123/// assert_eq!(flat_tree::parent(4), 5);
124/// ```
125#[inline]
126pub fn parent(i: u64) -> u64 {
127  let depth = self::depth(i);
128  index(depth + 1, offset(i) >> 1)
129}
130
131/// Returns the sibling of a node.
132///
133/// ## Examples
134/// ```rust
135/// assert_eq!(flat_tree::sibling(0), 2);
136/// assert_eq!(flat_tree::sibling(2), 0);
137/// assert_eq!(flat_tree::sibling(1), 5);
138/// assert_eq!(flat_tree::sibling(5), 1);
139/// ```
140#[inline]
141pub fn sibling(i: u64) -> u64 {
142  let depth = self::depth(i);
143  index(depth, offset(i) ^ 1)
144}
145
146/// Returns the parent's sibling, of a node.
147///
148/// ## Examples
149/// ```rust
150/// assert_eq!(flat_tree::uncle(0), 5);
151/// assert_eq!(flat_tree::uncle(2), 5);
152/// assert_eq!(flat_tree::uncle(1), 11);
153/// assert_eq!(flat_tree::uncle(5), 11);
154/// ```
155#[inline]
156pub fn uncle(i: u64) -> u64 {
157  let depth = self::depth(i);
158  index(depth + 1, offset(parent(i)) ^ 1)
159}
160
161/// Returns both children of a node.
162///
163/// ## Examples
164/// ```rust
165/// assert_eq!(flat_tree::children(0), None);
166/// assert_eq!(flat_tree::children(1), Some((0, 2)));
167/// assert_eq!(flat_tree::children(3), Some((1, 5)));
168/// assert_eq!(flat_tree::children(9), Some((8, 10)));
169/// ```
170#[inline]
171pub fn children(i: u64) -> Option<(u64, u64)> {
172  let depth = self::depth(i);
173  if is_even(i) {
174    None
175  } else if depth == 0 {
176    Some((i, i))
177  } else {
178    let offset = offset(i) * 2;
179    Some((index(depth - 1, offset), index(depth - 1, offset + 1)))
180  }
181}
182
183/// Returns only the left child of a node.
184///
185/// ## Examples
186/// ```rust
187/// assert_eq!(flat_tree::left_child(0), None);
188/// assert_eq!(flat_tree::left_child(1), Some(0));
189/// assert_eq!(flat_tree::left_child(3), Some(1));
190/// ```
191#[inline]
192pub fn left_child(i: u64) -> Option<u64> {
193  let depth = self::depth(i);
194  if is_even(i) {
195    None
196  } else if depth == 0 {
197    Some(i)
198  } else {
199    Some(index(depth - 1, offset(i) << 1))
200  }
201}
202
203/// Returns only the left child of a node.
204///
205/// ## Examples
206/// ```rust
207/// assert_eq!(flat_tree::right_child(0), None);
208/// assert_eq!(flat_tree::right_child(1), Some(2));
209/// assert_eq!(flat_tree::right_child(3), Some(5));
210/// ```
211// TODO: handle errors
212#[inline]
213pub fn right_child(i: u64) -> Option<u64> {
214  let depth = self::depth(i);
215  if is_even(i) {
216    None
217  } else if depth == 0 {
218    Some(i)
219  } else {
220    Some(index(depth - 1, (offset(i) << 1) + 1))
221  }
222}
223
224/// Returns the right most node in the tree that the node spans.
225///
226/// ## Examples
227/// ```rust
228/// assert_eq!(flat_tree::right_span(0), 0);
229/// assert_eq!(flat_tree::right_span(1), 2);
230/// assert_eq!(flat_tree::right_span(3), 6);
231/// assert_eq!(flat_tree::right_span(23), 30);
232/// assert_eq!(flat_tree::right_span(27), 30);
233/// ```
234#[inline]
235pub fn right_span(i: u64) -> u64 {
236  let depth = self::depth(i);
237  if depth == 0 {
238    i
239  } else {
240    (offset(i) + 1) * (2 << depth) - 2
241  }
242}
243
244/// Returns the left most node in the tree that it spans.
245///
246/// ## Examples
247/// ```rust
248/// assert_eq!(flat_tree::left_span(0), 0);
249/// assert_eq!(flat_tree::left_span(1), 0);
250/// assert_eq!(flat_tree::left_span(3), 0);
251/// assert_eq!(flat_tree::left_span(23), 16);
252/// assert_eq!(flat_tree::left_span(27), 24);
253/// ```
254#[inline]
255pub fn left_span(i: u64) -> u64 {
256  let depth = self::depth(i);
257  if depth == 0 {
258    i
259  } else {
260    offset(i) * (2 << depth)
261  }
262}
263
264/// Returns the left and right most nodes in the tree that the node spans.
265///
266/// ## Examples
267/// ```rust
268/// assert_eq!(flat_tree::spans(0), (0, 0));
269/// assert_eq!(flat_tree::spans(1), (0, 2));
270/// assert_eq!(flat_tree::spans(3), (0, 6));
271/// assert_eq!(flat_tree::spans(23), (16, 30));
272/// assert_eq!(flat_tree::spans(27), (24, 30));
273/// ```
274#[inline]
275pub fn spans(i: u64) -> (u64, u64) {
276  (left_span(i), right_span(i))
277}
278
279/// Returns how many nodes are in the tree that the node spans.
280///
281/// ## Examples
282/// ```rust
283/// assert_eq!(flat_tree::count(0), 1);
284/// assert_eq!(flat_tree::count(1), 3);
285/// assert_eq!(flat_tree::count(3), 7);
286/// assert_eq!(flat_tree::count(5), 3);
287/// assert_eq!(flat_tree::count(7), 15);
288/// assert_eq!(flat_tree::count(15), 31);
289/// assert_eq!(flat_tree::count(23), 15);
290/// assert_eq!(flat_tree::count(27), 7);
291/// ```
292#[inline]
293pub const fn count(i: u64) -> u64 {
294  let depth = self::depth(i);
295  (2 << depth) - 1
296}
297
298/// Returns how many leaves are in the tree that the node spans.
299///
300/// ## Examples
301/// ```rust
302/// assert_eq!(flat_tree::count_leaves(0), 1);
303/// assert_eq!(flat_tree::count_leaves(1), 2);
304/// assert_eq!(flat_tree::count_leaves(3), 4);
305/// assert_eq!(flat_tree::count_leaves(5), 2);
306/// assert_eq!(flat_tree::count_leaves(15), 16);
307/// assert_eq!(flat_tree::count_leaves(23), 8);
308/// assert_eq!(flat_tree::count_leaves(27), 4);
309/// ```
310#[inline]
311pub const fn count_leaves(i: u64) -> u64 {
312  (count(i) + 1) / 2
313}
314
315/// Returns a list of all the full roots (subtrees where all nodes have either 2
316/// or 0 children) `<` index.
317///
318/// For example `fullRoots(8)` returns `[3]` since the subtree rooted at `3`
319/// spans `0 -> 6`, and the tree rooted at `7` has a child located at `9` which
320/// is `>= 8`.
321///
322/// ## Panics
323/// If an uneven index is passed.
324///
325/// ## Examples
326/// ```rust
327/// use flat_tree::full_roots;
328///
329/// let mut nodes = Vec::with_capacity(16);
330/// full_roots(0, &mut nodes);
331/// assert_eq!(nodes, []);
332///
333/// let mut nodes = Vec::with_capacity(16);
334/// full_roots(2, &mut nodes);
335/// assert_eq!(nodes, [0]);
336///
337/// let mut nodes = Vec::with_capacity(16);
338/// full_roots(8, &mut nodes);
339/// assert_eq!(nodes, [3]);
340///
341/// let mut nodes = Vec::with_capacity(16);
342/// full_roots(20, &mut nodes);
343/// assert_eq!(nodes, [7, 17]);
344///
345/// let mut nodes = Vec::with_capacity(16);
346/// full_roots(18, &mut nodes);
347/// assert_eq!(nodes, [7, 16]);
348///
349/// let mut nodes = Vec::with_capacity(16);
350/// full_roots(16, &mut nodes);
351/// assert_eq!(nodes, [7]);
352///
353/// let mut nodes = Vec::with_capacity(16);
354/// full_roots(30, &mut nodes);
355/// assert_eq!(nodes, [7, 19, 25, 28]);
356
357/// ```
358#[inline]
359pub fn full_roots(i: u64, nodes: &mut Vec<u64>) {
360  assert!(
361    is_even(i),
362    "You can only look up roots for depth 0 blocks, got index {}",
363    i
364  );
365  let mut tmp = i >> 1;
366  let mut offset = 0;
367  let mut factor = 1;
368
369  loop {
370    if tmp == 0 {
371      break;
372    }
373    while factor * 2 <= tmp {
374      factor *= 2;
375    }
376    nodes.push(offset + factor - 1);
377    offset += 2 * factor;
378    tmp -= factor;
379    factor = 1;
380  }
381}
382
383#[inline]
384pub(crate) const fn is_even(num: u64) -> bool {
385  (num & 1) == 0
386}
387
388#[inline]
389pub(crate) const fn is_odd(num: u64) -> bool {
390  (num & 1) != 0
391}
392
393#[cfg(test)]
394mod tests {
395  use super::*;
396
397  #[test]
398  fn test_is_even() {
399    assert!(is_even(0));
400    assert!(!is_even(1));
401    assert!(is_even(2));
402    assert!(!is_even(3));
403  }
404
405  #[test]
406  fn test_is_odd() {
407    assert!(!is_odd(0));
408    assert!(is_odd(1));
409    assert!(!is_odd(2));
410    assert!(is_odd(3));
411  }
412
413  #[test]
414  fn test_parent_gt_int32() {
415    assert_eq!(parent(10_000_000_000), 10_000_000_001);
416  }
417
418  #[test]
419  fn test_child_to_parent_to_child() {
420    let mut child = 0;
421    for _ in 0..50 {
422      child = parent(child)
423    }
424    assert_eq!(child, 1_125_899_906_842_623);
425    for _ in 0..50 {
426      child = left_child(child).expect("no valid number returned");
427    }
428    assert_eq!(child, 0);
429  }
430}