use crate::containers::{Bitmap, Sequence};
use crate::triples::Id;
use std::cmp::Ordering;
#[derive(Debug)]
#[cfg_attr(feature = "cache", derive(serde::Deserialize, serde::Serialize))]
pub struct AdjList {
pub sequence: Sequence,
pub bitmap: Bitmap,
}
impl AdjList {
pub const fn new(sequence: Sequence, bitmap: Bitmap) -> Self {
AdjList { sequence, bitmap }
}
pub fn size_in_bytes(&self) -> usize {
self.sequence.size_in_bytes() + self.bitmap.size_in_bytes()
}
pub fn at_last_sibling(&self, word_index: usize) -> bool {
self.bitmap.at_last_sibling(word_index)
}
pub fn get_id(&self, word_index: usize) -> Id {
self.sequence.get(word_index) as Id
}
pub const fn len(&self) -> usize {
self.sequence.entries
}
pub const fn is_empty(&self) -> bool {
self.sequence.entries == 0
}
pub fn find(&self, x: Id) -> usize {
if x == 0 {
return 0;
}
self.bitmap.select1(x - 1).unwrap() as usize + 1
}
fn bin_search(&self, element: usize, begin: usize, end: usize) -> Option<usize> {
let mut low = begin;
let mut high = end;
while low < high {
let mid = usize::midpoint(low, high);
match (self.sequence.get(mid) as usize).cmp(&element) {
Ordering::Less => low = mid + 1,
Ordering::Greater => high = mid,
Ordering::Equal => return Some(mid),
}
}
None
}
pub fn search(&self, x: usize, y: usize) -> Option<usize> {
self.bin_search(y, self.find(x), self.last(x) + 1)
}
pub fn last(&self, x: Id) -> usize {
self.find(x + 1) - 1
}
}