use std::iter;
use std::mem;
use std::ops::Range;
use std::slice;
use std::vec;
use crate::BitVec;
use crate::BITS;
impl BitVec {
#[inline]
pub fn iter(&self) -> Iter<'_> {
Iter {
bit_vec: self,
idx: 0..self.len(),
}
}
}
#[derive(Clone)]
pub struct Iter<'a> {
bit_vec: &'a BitVec,
idx: Range<usize>,
}
impl<'a> Iterator for Iter<'a> {
type Item = bool;
#[inline]
fn next(&mut self) -> Option<bool> {
self.bit_vec.get(self.idx.next()?)
}
#[inline]
fn size_hint(&self) -> (usize, Option<usize>) {
self.idx.size_hint()
}
}
impl<'a> DoubleEndedIterator for Iter<'a> {
#[inline]
fn next_back(&mut self) -> Option<bool> {
self.bit_vec.get(self.idx.next_back()?)
}
}
impl<'a> ExactSizeIterator for Iter<'a> {}
impl<'a> IntoIterator for &'a BitVec {
type Item = bool;
type IntoIter = Iter<'a>;
#[inline]
fn into_iter(self) -> Iter<'a> {
self.iter()
}
}
impl BitVec {
#[inline]
pub fn ones_from(&self, from: usize) -> Ones<'_> {
let (byte, bit) = (from / BITS, from % BITS);
let mask = (!0) << bit;
let mut iter = self.as_bytes()[byte..].iter().copied();
let (current, _) = usize_from_bytes(&mut iter);
InnerOnes {
base: byte * BITS,
current: current & mask,
iter,
}
}
#[inline]
pub fn into_ones(self) -> IntoOnes {
let mut iter = self.into_bytes().into_iter();
let (current, _) = usize_from_bytes(&mut iter);
InnerOnes {
base: 0,
current,
iter,
}
}
}
pub type Ones<'a> = InnerOnes<iter::Copied<slice::Iter<'a, u8>>>;
pub type IntoOnes = InnerOnes<vec::IntoIter<u8>>;
#[derive(Clone)]
pub struct InnerOnes<I> {
base: usize,
current: usize,
iter: I,
}
impl<I: Iterator<Item = u8>> Iterator for InnerOnes<I> {
type Item = usize;
#[inline]
fn next(&mut self) -> Option<usize> {
let mut c = self.current;
while c == 0 {
let (next, done) = usize_from_bytes(&mut self.iter);
if done {
return None;
}
self.base += BITS * mem::size_of::<usize>();
c = next;
}
let lsb = c.trailing_zeros();
self.current = c & (c - 1);
Some(self.base + lsb as usize)
}
}
#[inline]
fn usize_from_bytes(iter: &mut impl Iterator<Item = u8>) -> (usize, bool) {
let mut n = 0;
for i in 0..mem::size_of::<usize>() {
match iter.next() {
Some(b) => n |= usize::from(b) << (i * BITS),
None => return (n, i == 0),
}
}
(n, false)
}
#[test]
fn iter_ones_from() {
let len = 5000;
let zeros = BitVec::from_elem(len, false);
assert_eq!(zeros.ones_from(0).next(), None);
let ones = BitVec::from_elem(len, true);
let mut iter = ones.ones_from(0);
for i in 0..len {
assert_eq!(iter.next(), Some(i));
assert_eq!(ones.ones_from(i).next(), Some(i));
}
let mut halves = BitVec::from_elem(len * 2, false);
for i in 0..len {
halves.set(i * 2, true);
}
let mut iter = halves.ones_from(0);
for i in 0..len {
assert_eq!(iter.next(), Some(i * 2));
assert_eq!(halves.ones_from(i * 2).next(), Some(i * 2));
if i > 0 {
assert_eq!(halves.ones_from(i * 2 - 1).next(), Some(i * 2));
}
assert_eq!(halves.ones_from(i).next(), Some(i + (i % 2)));
}
let mut sparse = BitVec::from_elem(len * 101, false);
for i in 0..len {
sparse.set(i * 101, true);
}
let mut iter = sparse.ones_from(0);
for i in 0..len {
let i101 = i * 101;
assert_eq!(iter.next(), Some(i101));
if i > 0 {
for j in i101 - 100..=i101 {
assert_eq!(sparse.ones_from(j).next(), Some(i101));
}
}
}
}
#[test]
fn iter_into_ones() {
let len = 5000;
let zeros = BitVec::from_elem(len, false);
assert_eq!(zeros.into_ones().next(), None);
let ones = BitVec::from_elem(len, true);
let mut iter = ones.into_ones();
for i in 0..len {
assert_eq!(iter.next(), Some(i));
}
let mut halves = BitVec::from_elem(len * 2, false);
for i in 0..len {
halves.set(i * 2, true);
}
let mut iter = halves.into_ones();
for i in 0..len {
assert_eq!(iter.next(), Some(i * 2));
}
let mut sparse = BitVec::from_elem(len * 101, false);
for i in 0..len {
sparse.set(i * 101, true);
}
let mut iter = sparse.into_ones();
for i in 0..len {
assert_eq!(iter.next(), Some(i * 101));
}
}