bitvek 0.3.8

A simple bit vector implementation.
Documentation
use crate::BitVec;
use core::cmp::min;
use core::iter::zip;

mod and;
mod not;
mod or;
mod xor;

impl BitVec {
    fn bitwise_operation<F>(&self, rhs: &Self, op: F) -> Self
    where
        F: FnMut((&usize, &usize)) -> usize,
    {
        let len = min(self.len, rhs.len);
        let data = zip(&self.data, &rhs.data).map(op).collect();
        Self { len, data }
    }

    fn bitwise_operation_consume_self<F>(self, rhs: &Self, op: F) -> Self
    where
        F: FnMut((usize, &usize)) -> usize,
    {
        let len = min(self.len, rhs.len);
        let data = zip(self.data, &rhs.data).map(op).collect();
        Self { len, data }
    }

    fn bitwise_operation_consume_both<F>(self, rhs: Self, op: F) -> Self
    where
        F: FnMut((usize, usize)) -> usize,
    {
        let len = min(self.len, rhs.len);
        let data = zip(self.data, rhs.data).map(op).collect();
        Self { len, data }
    }
}

#[cfg(test)]
mod tests {
    use crate::{BITS_PER_WORD, bitvec};

    const LONG: usize = BITS_PER_WORD * 2 - 2;
    const SHORT: usize = BITS_PER_WORD - 1;

    macro_rules! bitwise_assert {
        ($op:tt, ($input_1:expr, $input_2:expr) => $output:expr) => {
            let vec_1 = bitvec![$input_1; LONG];
            let vec_2 = bitvec![$input_2; SHORT];
            let expected = bitvec![$output; SHORT];

            assert_eq!(vec_1.clone() $op vec_2.clone(), expected);
            assert_eq!(vec_1.clone() $op &vec_2, expected);
            assert_eq!(&vec_1 $op vec_2.clone(), expected);
            assert_eq!(&vec_1 $op &vec_2, expected);

            assert_eq!(vec_2.clone() $op vec_1.clone(), expected);
            assert_eq!(vec_2.clone() $op &vec_1, expected);
            assert_eq!(&vec_2 $op vec_1.clone(), expected);
            assert_eq!(&vec_2 $op &vec_1, expected);
        };
    }

    #[test]
    fn test_bitand() {
        bitwise_assert!(&, (false, false) => false);
        bitwise_assert!(&, (false, true) => false);
        bitwise_assert!(&, (true, false) => false);
        bitwise_assert!(&, (true, true) => true);
    }

    #[test]
    fn test_bitor() {
        bitwise_assert!(|, (false, false) => false);
        bitwise_assert!(|, (false, true) => true);
        bitwise_assert!(|, (true, false) => true);
        bitwise_assert!(|, (true, true) => true);
    }

    #[test]
    fn test_bitxor() {
        bitwise_assert!(^, (false, false) => false);
        bitwise_assert!(^, (false, true) => true);
        bitwise_assert!(^, (true, false) => true);
        bitwise_assert!(^, (true, true) => false);
    }

    #[test]
    fn test_not() {
        let vec = bitvec![true; SHORT];
        let expected = bitvec![false; SHORT];
        assert_eq!(!&vec, expected);
        assert_eq!(!vec, expected);

        let vec = bitvec![false; LONG];
        let expected = bitvec![true; LONG];
        assert_eq!(!&vec, expected);
        assert_eq!(!vec, expected);
    }
}