pub trait BitAndAssign<Rhs = Self> {
    fn bitand_assign(&mut self, rhs: Rhs);
}
Expand description

The bitwise AND assignment operator &=.

Examples

An implementation of BitAndAssign that lifts the &= operator to a wrapper around bool.

use std::ops::BitAndAssign;

#[derive(Debug, PartialEq)]
struct Scalar(bool);

impl BitAndAssign for Scalar {
    // rhs is the "right-hand side" of the expression `a &= b`
    fn bitand_assign(&mut self, rhs: Self) {
        *self = Self(self.0 & rhs.0)
    }
}

let mut scalar = Scalar(true);
scalar &= Scalar(true);
assert_eq!(scalar, Scalar(true));

let mut scalar = Scalar(true);
scalar &= Scalar(false);
assert_eq!(scalar, Scalar(false));

let mut scalar = Scalar(false);
scalar &= Scalar(true);
assert_eq!(scalar, Scalar(false));

let mut scalar = Scalar(false);
scalar &= Scalar(false);
assert_eq!(scalar, Scalar(false));

Here, the BitAndAssign trait is implemented for a wrapper around Vec<bool>.

use std::ops::BitAndAssign;

#[derive(Debug, PartialEq)]
struct BooleanVector(Vec<bool>);

impl BitAndAssign for BooleanVector {
    // `rhs` is the "right-hand side" of the expression `a &= b`.
    fn bitand_assign(&mut self, rhs: Self) {
        assert_eq!(self.0.len(), rhs.0.len());
        *self = Self(
            self.0
                .iter()
                .zip(rhs.0.iter())
                .map(|(x, y)| *x & *y)
                .collect()
        );
    }
}

let mut bv = BooleanVector(vec![true, true, false, false]);
bv &= BooleanVector(vec![true, false, true, false]);
let expected = BooleanVector(vec![true, false, false, false]);
assert_eq!(bv, expected);

Required methods

Performs the &= operation.

Examples
let mut x = true;
x &= false;
assert_eq!(x, false);

let mut x = true;
x &= true;
assert_eq!(x, true);

let mut x: u8 = 5;
x &= 1;
assert_eq!(x, 1);

let mut x: u8 = 5;
x &= 2;
assert_eq!(x, 0);

Implementations on Foreign Types

Boolean Arithmetic

This merges another bit-slice into self with a Boolean arithmetic operation. If the other bit-slice is shorter than self, it is zero-extended. For BitAnd, this clears all excess bits of self to 0; for BitOr and BitXor, it leaves them untouched

Behavior

The Boolean operation proceeds across each bit-slice in iteration order. This is 3O(n) in the length of the shorter of self and rhs. However, it can be accelerated if rhs has the same type parameters as self, and both are using one of the orderings provided by bitvec. In this case, the implementation specializes to use BitField batch operations to operate on the slices one word at a time, rather than one bit.

Acceleration is not currently provided for custom bit-orderings that use the same storage type.

Pre-1.0 Behavior

In the 0. development series, Boolean arithmetic was implemented against all I: Iterator<Item = bool>. This allowed code such as bits |= [false, true];, but forbad acceleration in the most common use case (combining two bit-slices) because BitSlice is not such an iterator.

Usage surveys indicate that it is better for the arithmetic operators to operate on bit-slices, and to allow the possibility of specialized acceleration, rather than to allow folding against any iterator of bools.

If pre-1.0 code relies on this behavior specifically, and has non-BitSlice arguments to the Boolean sigils, then they will need to be replaced with the equivalent loop.

Examples
use bitvec::prelude::*;

let a = bits![mut 0, 0, 1, 1];
let b = bits![    0, 1, 0, 1];

*a ^= b;
assert_eq!(a, bits![0, 1, 1, 0]);

let c = bits![mut 0, 0, 1, 1];
let d = [false, true, false, true];

// no longer allowed
// c &= d.into_iter().by_vals();
for (mut c, d) in c.iter_mut().zip(d.into_iter())
{
  *c ^= d;
}
assert_eq!(c, bits![0, 1, 1, 0]);

Implementors