use super::storage::*;
use super::slice::*;
use super::traits::*;
use std::cmp::{max, Ordering};
use std::ptr;
mod inner;
use self::inner::Inner;
mod impls;
#[cfg(test)]
mod test;
#[derive(Clone)]
#[cfg_attr(feature = "serde", derive(Serialize))]
pub struct BitVec<Block: BlockType = usize> {
bits: Inner<Block>,
len: u64,
}
#[cfg(feature = "serde")]
impl<'de, Block: BlockType + serde::Deserialize<'de>> serde::Deserialize<'de> for BitVec<Block> {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: serde::Deserializer<'de>,
{
#[derive(Deserialize)]
struct Unchecked<Block: BlockType> {
bits: Inner<Block>,
len: u64,
}
let unchecked = Unchecked::deserialize(deserializer)?;
let unchecked = BitVec {
bits: unchecked.bits,
len: unchecked.len,
};
if !unchecked.invariant() {
return Err(serde::de::Error::custom("Invalid BitVec"));
}
Ok(unchecked)
}
}
impl<Block: BlockType> Default for BitVec<Block> {
fn default() -> Self {
Self::new()
}
}
impl<Block: BlockType> BitVec<Block> {
#[allow(dead_code)]
fn invariant(&self) -> bool {
return self.len <= Block::mul_nbits(self.bits.len());
}
pub fn new() -> Self {
Self::with_block_capacity(0)
}
pub fn with_capacity(nbits: u64) -> Self {
Self::with_block_capacity(Block::ceil_div_nbits(nbits))
}
pub fn with_block_capacity(nblocks: usize) -> Self {
let mut result = Self::from_block(Block::zero(), nblocks);
result.len = 0;
result
}
pub fn new_fill(value: bool, len: u64) -> Self {
let mut result = Self::new_block_fill(value, Block::ceil_div_nbits(len));
result.len = len;
result
}
#[inline]
fn new_block_fill(value: bool, nblocks: usize) -> Self {
let block = if value {!Block::zero()} else {Block::zero()};
Self::from_block(block, nblocks)
}
#[inline]
fn from_block(init: Block, nblocks: usize) -> Self {
BitVec {
bits: Inner::new(init, nblocks),
len: Block::mul_nbits(nblocks),
}
}
fn reallocate(&mut self, block_cap: usize) {
unsafe {
self.bits = self.bits.clone_resize(self.block_len(), block_cap);
}
}
pub fn from_bits<B: Bits<Block = Block>>(bits: B) -> Self {
let block_len = bits.block_len();
let mut vec: Vec<Block> = Vec::with_capacity(block_len);
unsafe {
let ptr = vec.as_mut_ptr();
for i in 0 .. block_len {
ptr::write(ptr.offset(i as isize), bits.get_raw_block(i));
}
vec.set_len(block_len);
}
let mut result: BitVec<Block> = vec.into();
result.resize(bits.bit_len(), false);
result
}
#[inline]
pub fn len(&self) -> u64 {
self.len
}
pub fn block_len(&self) -> usize {
Block::ceil_div_nbits(self.len())
}
pub fn capacity(&self) -> u64 {
Block::mul_nbits(self.block_capacity())
}
pub fn block_capacity(&self) -> usize {
self.bits.len()
}
pub fn reserve(&mut self, additional: u64) {
let old_cap = self.capacity();
let req_cap = self.len() + additional;
if req_cap > old_cap {
self.reserve_exact(max(additional, old_cap));
}
}
pub fn block_reserve(&mut self, additional: usize) {
let old_cap = self.block_capacity();
let req_cap = self.block_len() + additional;
if req_cap > old_cap {
self.block_reserve_exact(max(additional, old_cap));
}
}
pub fn reserve_exact(&mut self, additional: u64) {
let new_cap = Block::ceil_div_nbits(self.len() + additional);
if new_cap > self.block_capacity() {
self.reallocate(new_cap);
}
}
pub fn block_reserve_exact(&mut self, additional: usize) {
let new_cap = self.block_len() + additional;
if new_cap > self.block_capacity() {
self.reallocate(new_cap);
}
}
pub fn shrink_to_fit(&mut self) {
let block_len = self.block_len();
if self.block_capacity() > block_len {
self.reallocate(block_len);
}
}
pub fn into_boxed_slice(self) -> Box<[Block]> {
self.bits.into_boxed_slice()
}
pub fn truncate(&mut self, len: u64) {
if len < self.len {
self.len = len;
}
}
pub fn resize(&mut self, len: u64, value: bool) {
match len.cmp(&self.len) {
Ordering::Less => {
self.len = len
},
Ordering::Equal => { },
Ordering::Greater => {
{
let growth = len - self.len();
self.reserve(growth);
}
self.align_block(value);
let block = if value {!Block::zero()} else {Block::zero()};
while self.len < len {
self.push_block(block);
}
self.len = len;
},
}
}
pub fn as_slice(&self) -> BitSlice<Block> {
unsafe {
BitSlice::from_raw_parts(self.bits.as_ptr(), 0, self.len)
}
}
pub fn as_mut_slice(&mut self) -> BitSliceMut<Block> {
unsafe {
BitSliceMut::from_raw_parts(self.bits.as_mut_ptr(), 0, self.len)
}
}
pub fn get(&self, position: u64) -> bool {
self.get_bit(position)
}
pub fn set(&mut self, position: u64, value: bool) {
self.set_bit(position, value);
}
pub fn push(&mut self, value: bool) {
self.reserve(1);
let old_len = self.len;
self.len = old_len + 1;
self.set_bit(old_len, value);
}
pub fn pop(&mut self) -> Option<bool> {
if self.len > 0 {
let new_len = self.len - 1;
let result = self.get_bit(new_len);
self.len = new_len;
Some(result)
} else {
None
}
}
pub fn clear(&mut self) {
self.len = 0;
}
pub fn is_empty(&self) -> bool {
self.len == 0
}
}