diff --git a/src/lib.rs b/src/lib.rs index 368eccf..0eded97 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -303,6 +303,8 @@ impl FixedBitSet } /// In-place union of two `FixedBitSet`s. + /// + /// On calling this method, `self`'s capacity may be increased to match `other`'s. pub fn union_with(&mut self, other: &FixedBitSet) { if other.len() >= self.len() { @@ -314,6 +316,8 @@ impl FixedBitSet } /// In-place intersection of two `FixedBitSet`s. + /// + /// On calling this method, `self`'s capacity will remain the same as before. pub fn intersect_with(&mut self, other: &FixedBitSet) { for (x, y) in self.data.iter_mut().zip(other.data.iter()) { @@ -325,7 +329,26 @@ impl FixedBitSet } } + /// In-place difference of two `FixedBitSet`s. + /// + /// On calling this method, `self`'s capacity will remain the same as before. + pub fn difference_with(&mut self, other: &FixedBitSet) + { + for (x, y) in self.data.iter_mut().zip(other.data.iter()) { + *x &= !*y; + } + + // There's no need to grow self or do any other adjustments. + // + // * If self is longer than other, the bits at the end of self won't be affected since other + // has them implicitly set to 0. + // * If other is longer than self, the bits at the end of other are irrelevant since self + // has them set to 0 anyway. + } + /// In-place symmetric difference of two `FixedBitSet`s. + /// + /// On calling this method, `self`'s capacity may be increased to match `other`'s. pub fn symmetric_difference_with(&mut self, other: &FixedBitSet) { if other.len() >= self.len() { @@ -965,7 +988,7 @@ fn intersection() { a.set_range(..a_end, true); b.set_range(b_start.., true); - let ab = a.intersection(&b).collect::(); + let mut ab = a.intersection(&b).collect::(); for i in 0..b_start { assert!(!ab.contains(i)); @@ -976,6 +999,11 @@ fn intersection() { for i in a_end..len { assert!(!ab.contains(i)); } + + a.intersect_with(&b); + // intersection + collect produces the same results but with a shorter length. + ab.grow(a.len()); + assert_eq!(ab, a, "intersection and intersect_with produce the same results"); } #[test] @@ -998,6 +1026,9 @@ fn union() { for i in b_end..a_start { assert!(!ab.contains(i)); } + + a.union_with(&b); + assert_eq!(ab, a, "union and union_with produce the same results"); } #[test] @@ -1011,13 +1042,18 @@ fn difference() { let mut b = FixedBitSet::with_capacity(b_len); a.set_range(a_start..a_end, true); b.set_range(b_start..b_len, true); - let a_diff_b = a.difference(&b).collect::(); + let mut a_diff_b = a.difference(&b).collect::(); for i in a_start..b_start { assert!(a_diff_b.contains(i)); } for i in b_start..b_len { assert!(!a_diff_b.contains(i)); } + + a.difference_with(&b); + // difference + collect produces the same results but with a shorter length. + a_diff_b.grow(a.len()); + assert_eq!(a_diff_b, a, "difference and difference_with produce the same results"); } #[test] @@ -1044,6 +1080,9 @@ fn symmetric_difference() { for i in a_end..b_len { assert!(a_sym_diff_b.contains(i)); } + + a.symmetric_difference_with(&b); + assert_eq!(a_sym_diff_b, a, "symmetric_difference and _with produce the same results"); } #[test]