mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-04-09 01:38:03 +00:00
Several fixes:
(1) Applied patch from Casey to implement iterator::operator= correctly: it should use a pointer, not a reference. (2) Added operators == and !=, and method all(). (3) Important bug fix: excess bits need to be ignored in operations like ==, count(), and all(). We do this by ensuring excess bits in the last bitset are always 0. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@4837 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
61ff02982f
commit
0e2cf7606d
@ -36,14 +36,26 @@
|
||||
|
||||
|
||||
class BitSetVector {
|
||||
// Types used internal to the representation
|
||||
typedef std::bitset<WORDSIZE> bitword;
|
||||
typedef bitword::reference reference;
|
||||
class iterator;
|
||||
|
||||
// Data used in the representation
|
||||
std::vector<bitword> bitsetVec;
|
||||
unsigned maxSize;
|
||||
|
||||
private:
|
||||
// Utility functions for the representation
|
||||
static unsigned NumWords(unsigned Size) { return (Size+WORDSIZE-1)/WORDSIZE;}
|
||||
static unsigned LastWordSize(unsigned Size) { return Size % WORDSIZE; }
|
||||
|
||||
// Clear the unused bits in the last word.
|
||||
// The unused bits are the high (WORDSIZE - LastWordSize()) bits
|
||||
void ClearUnusedBits() {
|
||||
unsigned long usedBits = (1U << LastWordSize(size())) - 1;
|
||||
bitsetVec.back() &= bitword(usedBits);
|
||||
}
|
||||
|
||||
const bitword& getWord(unsigned i) const { return bitsetVec[i]; }
|
||||
bitword& getWord(unsigned i) { return bitsetVec[i]; }
|
||||
@ -68,29 +80,42 @@ public:
|
||||
/// Modifier methods: reset, set for entire set, operator[] for one element.
|
||||
///
|
||||
void reset() {
|
||||
for(std::vector<bitword>::iterator I=bitsetVec.begin(), E=bitsetVec.end();
|
||||
I != E; ++I)
|
||||
I->reset();
|
||||
for (unsigned i=0, N = bitsetVec.size(); i < N; ++i)
|
||||
bitsetVec[i].reset();
|
||||
}
|
||||
void set() {
|
||||
for(std::vector<bitword>::iterator I=bitsetVec.begin(), E=bitsetVec.end();
|
||||
I != E; ++I)
|
||||
I->set();
|
||||
for (unsigned i=0, N = bitsetVec.size(); i < N; ++i) // skip last word
|
||||
bitsetVec[i].set();
|
||||
ClearUnusedBits();
|
||||
}
|
||||
std::bitset<32>::reference operator[](unsigned n) {
|
||||
reference operator[](unsigned n) {
|
||||
assert(n < size() && "BitSetVector: Bit number out of range");
|
||||
unsigned ndiv = n / WORDSIZE, nmod = n % WORDSIZE;
|
||||
assert(ndiv < bitsetVec.size() && "BitSetVector: Bit number out of range");
|
||||
return bitsetVec[ndiv][nmod];
|
||||
}
|
||||
iterator begin() { return iterator::begin(*this); }
|
||||
iterator end() { return iterator::end(*this); }
|
||||
|
||||
///
|
||||
/// Comparison operations: equal, not equal
|
||||
///
|
||||
bool operator == (const BitSetVector& set2) const {
|
||||
assert(maxSize == set2.maxSize && "Illegal == comparison");
|
||||
for (unsigned i = 0; i < bitsetVec.size(); ++i)
|
||||
if (getWord(i) != set2.getWord(i))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
bool operator != (const BitSetVector& set2) const {
|
||||
return ! (*this == set2);
|
||||
}
|
||||
|
||||
///
|
||||
/// Set membership operations: single element, any, none, count
|
||||
///
|
||||
bool test(unsigned n) const {
|
||||
assert(n < size() && "BitSetVector: Bit number out of range");
|
||||
unsigned ndiv = n / WORDSIZE, nmod = n % WORDSIZE;
|
||||
assert(ndiv < bitsetVec.size() && "BitSetVector: Bit number out of range");
|
||||
return bitsetVec[ndiv].test(nmod);
|
||||
}
|
||||
bool any() const {
|
||||
@ -108,6 +133,9 @@ public:
|
||||
n += bitsetVec[i].count();
|
||||
return n;
|
||||
}
|
||||
bool all() const {
|
||||
return (count() == size());
|
||||
}
|
||||
|
||||
///
|
||||
/// Set operations: intersection, union, disjoint union, complement.
|
||||
@ -137,6 +165,7 @@ public:
|
||||
BitSetVector result(maxSize);
|
||||
for (unsigned i = 0; i < bitsetVec.size(); ++i)
|
||||
(result.getWord(i) = getWord(i)).flip();
|
||||
result.ClearUnusedBits();
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -156,12 +185,12 @@ public:
|
||||
class iterator {
|
||||
unsigned currentBit;
|
||||
unsigned currentWord;
|
||||
BitSetVector& bitvec;
|
||||
iterator(unsigned B, unsigned W, BitSetVector _bitvec)
|
||||
: currentBit(B), currentWord(W), bitvec(_bitvec) { }
|
||||
BitSetVector* bitvec;
|
||||
iterator(unsigned B, unsigned W, BitSetVector& _bitvec)
|
||||
: currentBit(B), currentWord(W), bitvec(&_bitvec) { }
|
||||
public:
|
||||
iterator(BitSetVector& _bitvec)
|
||||
: currentBit(0), currentWord(0), bitvec(_bitvec) { }
|
||||
: currentBit(0), currentWord(0), bitvec(&_bitvec) { }
|
||||
iterator(const iterator& I)
|
||||
: currentBit(I.currentBit),currentWord(I.currentWord),bitvec(I.bitvec) { }
|
||||
iterator& operator=(const iterator& I) {
|
||||
@ -174,13 +203,13 @@ public:
|
||||
// Increment and decrement operators (pre and post)
|
||||
iterator& operator++() {
|
||||
if (++currentBit == WORDSIZE)
|
||||
{ currentBit = 0; if (currentWord < bitvec.maxSize) ++currentWord; }
|
||||
{ currentBit = 0; if (currentWord < bitvec->maxSize) ++currentWord; }
|
||||
return *this;
|
||||
}
|
||||
iterator& operator--() {
|
||||
if (currentBit == 0) {
|
||||
currentBit = WORDSIZE-1;
|
||||
currentWord = (currentWord == 0)? bitvec.maxSize : --currentWord;
|
||||
currentWord = (currentWord == 0)? bitvec->maxSize : --currentWord;
|
||||
}
|
||||
else
|
||||
--currentBit;
|
||||
@ -191,14 +220,14 @@ public:
|
||||
|
||||
// Dereferencing operators
|
||||
reference operator*() {
|
||||
assert(currentWord < bitvec.maxSize &&
|
||||
assert(currentWord < bitvec->maxSize &&
|
||||
"Dereferencing iterator past the end of a BitSetVector");
|
||||
return bitvec.getWord(currentWord)[currentBit];
|
||||
return bitvec->getWord(currentWord)[currentBit];
|
||||
}
|
||||
|
||||
// Comparison operator
|
||||
bool operator==(const iterator& I) {
|
||||
return (&I.bitvec == &bitvec &&
|
||||
return (I.bitvec == bitvec &&
|
||||
I.currentWord == currentWord && I.currentBit == currentBit);
|
||||
}
|
||||
|
||||
|
@ -36,14 +36,26 @@
|
||||
|
||||
|
||||
class BitSetVector {
|
||||
// Types used internal to the representation
|
||||
typedef std::bitset<WORDSIZE> bitword;
|
||||
typedef bitword::reference reference;
|
||||
class iterator;
|
||||
|
||||
// Data used in the representation
|
||||
std::vector<bitword> bitsetVec;
|
||||
unsigned maxSize;
|
||||
|
||||
private:
|
||||
// Utility functions for the representation
|
||||
static unsigned NumWords(unsigned Size) { return (Size+WORDSIZE-1)/WORDSIZE;}
|
||||
static unsigned LastWordSize(unsigned Size) { return Size % WORDSIZE; }
|
||||
|
||||
// Clear the unused bits in the last word.
|
||||
// The unused bits are the high (WORDSIZE - LastWordSize()) bits
|
||||
void ClearUnusedBits() {
|
||||
unsigned long usedBits = (1U << LastWordSize(size())) - 1;
|
||||
bitsetVec.back() &= bitword(usedBits);
|
||||
}
|
||||
|
||||
const bitword& getWord(unsigned i) const { return bitsetVec[i]; }
|
||||
bitword& getWord(unsigned i) { return bitsetVec[i]; }
|
||||
@ -68,29 +80,42 @@ public:
|
||||
/// Modifier methods: reset, set for entire set, operator[] for one element.
|
||||
///
|
||||
void reset() {
|
||||
for(std::vector<bitword>::iterator I=bitsetVec.begin(), E=bitsetVec.end();
|
||||
I != E; ++I)
|
||||
I->reset();
|
||||
for (unsigned i=0, N = bitsetVec.size(); i < N; ++i)
|
||||
bitsetVec[i].reset();
|
||||
}
|
||||
void set() {
|
||||
for(std::vector<bitword>::iterator I=bitsetVec.begin(), E=bitsetVec.end();
|
||||
I != E; ++I)
|
||||
I->set();
|
||||
for (unsigned i=0, N = bitsetVec.size(); i < N; ++i) // skip last word
|
||||
bitsetVec[i].set();
|
||||
ClearUnusedBits();
|
||||
}
|
||||
std::bitset<32>::reference operator[](unsigned n) {
|
||||
reference operator[](unsigned n) {
|
||||
assert(n < size() && "BitSetVector: Bit number out of range");
|
||||
unsigned ndiv = n / WORDSIZE, nmod = n % WORDSIZE;
|
||||
assert(ndiv < bitsetVec.size() && "BitSetVector: Bit number out of range");
|
||||
return bitsetVec[ndiv][nmod];
|
||||
}
|
||||
iterator begin() { return iterator::begin(*this); }
|
||||
iterator end() { return iterator::end(*this); }
|
||||
|
||||
///
|
||||
/// Comparison operations: equal, not equal
|
||||
///
|
||||
bool operator == (const BitSetVector& set2) const {
|
||||
assert(maxSize == set2.maxSize && "Illegal == comparison");
|
||||
for (unsigned i = 0; i < bitsetVec.size(); ++i)
|
||||
if (getWord(i) != set2.getWord(i))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
bool operator != (const BitSetVector& set2) const {
|
||||
return ! (*this == set2);
|
||||
}
|
||||
|
||||
///
|
||||
/// Set membership operations: single element, any, none, count
|
||||
///
|
||||
bool test(unsigned n) const {
|
||||
assert(n < size() && "BitSetVector: Bit number out of range");
|
||||
unsigned ndiv = n / WORDSIZE, nmod = n % WORDSIZE;
|
||||
assert(ndiv < bitsetVec.size() && "BitSetVector: Bit number out of range");
|
||||
return bitsetVec[ndiv].test(nmod);
|
||||
}
|
||||
bool any() const {
|
||||
@ -108,6 +133,9 @@ public:
|
||||
n += bitsetVec[i].count();
|
||||
return n;
|
||||
}
|
||||
bool all() const {
|
||||
return (count() == size());
|
||||
}
|
||||
|
||||
///
|
||||
/// Set operations: intersection, union, disjoint union, complement.
|
||||
@ -137,6 +165,7 @@ public:
|
||||
BitSetVector result(maxSize);
|
||||
for (unsigned i = 0; i < bitsetVec.size(); ++i)
|
||||
(result.getWord(i) = getWord(i)).flip();
|
||||
result.ClearUnusedBits();
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -156,12 +185,12 @@ public:
|
||||
class iterator {
|
||||
unsigned currentBit;
|
||||
unsigned currentWord;
|
||||
BitSetVector& bitvec;
|
||||
iterator(unsigned B, unsigned W, BitSetVector _bitvec)
|
||||
: currentBit(B), currentWord(W), bitvec(_bitvec) { }
|
||||
BitSetVector* bitvec;
|
||||
iterator(unsigned B, unsigned W, BitSetVector& _bitvec)
|
||||
: currentBit(B), currentWord(W), bitvec(&_bitvec) { }
|
||||
public:
|
||||
iterator(BitSetVector& _bitvec)
|
||||
: currentBit(0), currentWord(0), bitvec(_bitvec) { }
|
||||
: currentBit(0), currentWord(0), bitvec(&_bitvec) { }
|
||||
iterator(const iterator& I)
|
||||
: currentBit(I.currentBit),currentWord(I.currentWord),bitvec(I.bitvec) { }
|
||||
iterator& operator=(const iterator& I) {
|
||||
@ -174,13 +203,13 @@ public:
|
||||
// Increment and decrement operators (pre and post)
|
||||
iterator& operator++() {
|
||||
if (++currentBit == WORDSIZE)
|
||||
{ currentBit = 0; if (currentWord < bitvec.maxSize) ++currentWord; }
|
||||
{ currentBit = 0; if (currentWord < bitvec->maxSize) ++currentWord; }
|
||||
return *this;
|
||||
}
|
||||
iterator& operator--() {
|
||||
if (currentBit == 0) {
|
||||
currentBit = WORDSIZE-1;
|
||||
currentWord = (currentWord == 0)? bitvec.maxSize : --currentWord;
|
||||
currentWord = (currentWord == 0)? bitvec->maxSize : --currentWord;
|
||||
}
|
||||
else
|
||||
--currentBit;
|
||||
@ -191,14 +220,14 @@ public:
|
||||
|
||||
// Dereferencing operators
|
||||
reference operator*() {
|
||||
assert(currentWord < bitvec.maxSize &&
|
||||
assert(currentWord < bitvec->maxSize &&
|
||||
"Dereferencing iterator past the end of a BitSetVector");
|
||||
return bitvec.getWord(currentWord)[currentBit];
|
||||
return bitvec->getWord(currentWord)[currentBit];
|
||||
}
|
||||
|
||||
// Comparison operator
|
||||
bool operator==(const iterator& I) {
|
||||
return (&I.bitvec == &bitvec &&
|
||||
return (I.bitvec == bitvec &&
|
||||
I.currentWord == currentWord && I.currentBit == currentBit);
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user