mirror of
https://github.com/fluencelabs/tendermint
synced 2025-06-23 09:41:38 +00:00
bit_array: Simplify subtraction
also, fix potential bug in Or function
This commit is contained in:
committed by
Anton Kaliaev
parent
c94133ed1b
commit
0755a5203d
@ -119,14 +119,13 @@ func (bA *BitArray) Or(o *BitArray) *BitArray {
|
||||
}
|
||||
bA.mtx.Lock()
|
||||
o.mtx.Lock()
|
||||
defer func() {
|
||||
bA.mtx.Unlock()
|
||||
o.mtx.Unlock()
|
||||
}()
|
||||
c := bA.copyBits(MaxInt(bA.Bits, o.Bits))
|
||||
for i := 0; i < len(c.Elems); i++ {
|
||||
smaller := MinInt(len(bA.Elems), len(o.Elems))
|
||||
for i := 0; i < smaller; i++ {
|
||||
c.Elems[i] |= o.Elems[i]
|
||||
}
|
||||
bA.mtx.Unlock()
|
||||
o.mtx.Unlock()
|
||||
return c
|
||||
}
|
||||
|
||||
@ -173,8 +172,9 @@ func (bA *BitArray) not() *BitArray {
|
||||
}
|
||||
|
||||
// Sub subtracts the two bit-arrays bitwise, without carrying the bits.
|
||||
// This is essentially bA.And(o.Not()).
|
||||
// If bA is longer than o, o is right padded with zeroes.
|
||||
// Note that carryless subtraction of a - b is (a and not b).
|
||||
// The output is the same as bA, regardless of o's size.
|
||||
// If bA is longer than o, o is right padded with zeroes
|
||||
func (bA *BitArray) Sub(o *BitArray) *BitArray {
|
||||
if bA == nil || o == nil {
|
||||
// TODO: Decide if we should do 1's complement here?
|
||||
@ -182,24 +182,20 @@ func (bA *BitArray) Sub(o *BitArray) *BitArray {
|
||||
}
|
||||
bA.mtx.Lock()
|
||||
o.mtx.Lock()
|
||||
defer func() {
|
||||
bA.mtx.Unlock()
|
||||
o.mtx.Unlock()
|
||||
}()
|
||||
if bA.Bits > o.Bits {
|
||||
c := bA.copy()
|
||||
for i := 0; i < len(o.Elems)-1; i++ {
|
||||
c.Elems[i] &= ^o.Elems[i]
|
||||
}
|
||||
i := len(o.Elems) - 1
|
||||
if i >= 0 {
|
||||
for idx := i * 64; idx < o.Bits; idx++ {
|
||||
c.setIndex(idx, c.getIndex(idx) && !o.getIndex(idx))
|
||||
}
|
||||
}
|
||||
return c
|
||||
// output is the same size as bA
|
||||
c := bA.copyBits(bA.Bits)
|
||||
// Only iterate to the minimum size between the two.
|
||||
// If o is longer, those bits are ignored.
|
||||
// If bA is longer, then skipping those iterations is equivalent
|
||||
// to right padding with 0's
|
||||
smaller := MinInt(len(bA.Elems), len(o.Elems))
|
||||
for i := 0; i < smaller; i++ {
|
||||
// &^ is and not in golang
|
||||
c.Elems[i] &^= o.Elems[i]
|
||||
}
|
||||
return bA.and(o.not()) // Note degenerate case where o == nil
|
||||
bA.mtx.Unlock()
|
||||
o.mtx.Unlock()
|
||||
return c
|
||||
}
|
||||
|
||||
// IsEmpty returns true iff all bits in the bit array are 0
|
||||
|
Reference in New Issue
Block a user