1 // This may look like C code, but it is really -*- C++ -*-
3 Copyright (C) 1988 Free Software Foundation
4 written by Doug Lea (dl@rocky.oswego.edu)
6 This file is part of GNU CC.
8 GNU CC is distributed in the hope that it will be useful,
9 but WITHOUT ANY WARRANTY. No author or distributor
10 accepts responsibility to anyone for the consequences of using it
11 or for whether it serves any particular purpose or works at all,
12 unless he says so in writing. Refer to the GNU CC General Public
13 License for full details.
15 Everyone is granted permission to copy, modify and redistribute
16 GNU CC, but only under the conditions described in the
17 GNU CC General Public License. A copy of this license is
18 supposed to have been given to you along with GNU CC so you
19 can know your rights and responsibilities. It should be in a
20 file named COPYING. Among other things, the copyright notice
21 and this notice must be preserved on all copies.
35 #define BITSETBITS BITS(short)
39 unsigned short len
; // number of shorts in s
40 unsigned short sz
; // allocated slots
41 unsigned short virt
; // virtual 0 or 1
42 unsigned short s
[1]; // bits start here
45 extern BitSetRep
* BitSetalloc(BitSetRep
*, const unsigned short*,
47 extern BitSetRep
* BitSetcopy(BitSetRep
*, const BitSetRep
*);
48 extern BitSetRep
* BitSetresize(BitSetRep
*, int);
49 extern BitSetRep
* BitSetop(const BitSetRep
*, const BitSetRep
*,
51 extern BitSetRep
* BitSetcmpl(const BitSetRep
*, BitSetRep
*);
54 extern BitSetRep _nilBitSetRep
;
65 BitSetBit(BitSet
* v
, int p
);
66 BitSetBit(const BitSetBit
& b
);
69 int operator = (int b
);
70 int operator == (int b
);
71 int operator != (int b
);
84 BitSet(const BitSet
&);
88 void operator = (const BitSet
& y
);
90 // equality & subset tests
92 friend int operator == (const BitSet
& x
, const BitSet
& y
);
93 friend int operator != (const BitSet
& x
, const BitSet
& y
);
94 friend int operator < (const BitSet
& x
, const BitSet
& y
);
95 friend int operator <= (const BitSet
& x
, const BitSet
& y
);
96 friend int operator > (const BitSet
& x
, const BitSet
& y
);
97 friend int operator >= (const BitSet
& x
, const BitSet
& y
);
100 // operations on self
102 void operator |= (const BitSet
& y
);
103 void operator &= (const BitSet
& y
);
104 void operator -= (const BitSet
& y
);
105 void operator ^= (const BitSet
& y
);
109 // individual bit manipulation
112 void set(int from
, int to
);
113 void set(); // set all
116 void clear(int from
, int to
);
117 void clear(); // clear all
119 void invert(int pos
);
120 void invert(int from
, int to
);
122 int test(int pos
) const;
123 int test(int from
, int to
) const;
125 BitSetBit
operator [] (int i
);
129 int first(int b
= 1) const;
130 int last(int b
= 1) const;
132 int next(int pos
, int b
= 1) const;
133 int previous(int pos
, int b
= 1) const;
138 int virtual_bit() const;
139 int count(int b
= 1) const;
143 friend BitSet
atoBitSet(const char* s
,
144 char f
='0', char t
='1', char star
='*');
145 friend const char* BitSettoa(const BitSet
& x
,
146 char f
='0', char t
='1', char star
='*');
148 friend BitSet
shorttoBitSet(unsigned short w
);
149 friend BitSet
longtoBitSet(unsigned long w
);
151 friend ostream
& operator << (ostream
& s
, const BitSet
& x
);
153 // procedural versions of operators
155 friend void and(const BitSet
& x
, const BitSet
& y
, BitSet
& r
);
156 friend void or(const BitSet
& x
, const BitSet
& y
, BitSet
& r
);
157 friend void xor(const BitSet
& x
, const BitSet
& y
, BitSet
& r
);
158 friend void diff(const BitSet
& x
, const BitSet
& y
, BitSet
& r
);
159 friend void complement(const BitSet
& x
, BitSet
& r
);
163 volatile void error(const char* msg
) const;
168 typedef BitSet BitSetTmp
;
171 BitSet
operator | (const BitSet
& x
, const BitSet
& y
);
172 BitSet
operator & (const BitSet
& x
, const BitSet
& y
);
173 BitSet
operator - (const BitSet
& x
, const BitSet
& y
);
174 BitSet
operator ^ (const BitSet
& x
, const BitSet
& y
);
176 BitSet
operator ~ (const BitSet
& x
);
178 // These are inlined regardless of optimization
180 inline int BitSet_index(int l
)
182 return (unsigned)(l
) / BITSETBITS
;
185 inline int BitSet_pos(int l
)
187 return l
& (BITSETBITS
- 1);
190 #if defined(__OPTIMIZE__) || defined(USE_LIBGXX_INLINES)
193 inline BitSet::BitSet() : rep(&_nilBitSetRep
) {}
195 inline BitSet::BitSet(const BitSet
& x
) :rep(BitSetcopy(0, x
.rep
)) {}
197 inline BitSet::~BitSet() { if (rep
!= &_nilBitSetRep
) delete rep
; }
199 inline void BitSet::operator = (const BitSet
& y
)
201 rep
= BitSetcopy(rep
, y
.rep
);
204 inline int operator != (const BitSet
& x
, const BitSet
& y
) { return !(x
== y
); }
206 inline int operator > (const BitSet
& x
, const BitSet
& y
) { return y
< x
; }
208 inline int operator >= (const BitSet
& x
, const BitSet
& y
) { return y
<= x
; }
210 inline void and(const BitSet
& x
, const BitSet
& y
, BitSet
& r
)
212 r
.rep
= BitSetop(x
.rep
, y
.rep
, r
.rep
, '&');
215 inline void or(const BitSet
& x
, const BitSet
& y
, BitSet
& r
)
217 r
.rep
= BitSetop(x
.rep
, y
.rep
, r
.rep
, '|');
220 inline void xor(const BitSet
& x
, const BitSet
& y
, BitSet
& r
)
222 r
.rep
= BitSetop(x
.rep
, y
.rep
, r
.rep
, '^');
225 inline void diff(const BitSet
& x
, const BitSet
& y
, BitSet
& r
)
227 r
.rep
= BitSetop(x
.rep
, y
.rep
, r
.rep
, '-');
230 inline void complement(const BitSet
& x
, BitSet
& r
)
232 r
.rep
= BitSetcmpl(x
.rep
, r
.rep
);
235 #if defined(__GNUG__) && !defined(NO_NRV)
237 inline BitSet
operator & (const BitSet
& x
, const BitSet
& y
) return r
242 inline BitSet
operator | (const BitSet
& x
, const BitSet
& y
) return r
247 inline BitSet
operator ^ (const BitSet
& x
, const BitSet
& y
) return r
252 inline BitSet
operator - (const BitSet
& x
, const BitSet
& y
) return r
257 inline BitSet
operator ~ (const BitSet
& x
) return r
264 inline BitSet
operator & (const BitSet
& x
, const BitSet
& y
)
266 BitSet r
; and(x
, y
, r
); return r
;
269 inline BitSet
operator | (const BitSet
& x
, const BitSet
& y
)
271 BitSet r
; or(x
, y
, r
); return r
;
274 inline BitSet
operator ^ (const BitSet
& x
, const BitSet
& y
)
276 BitSet r
; xor(x
, y
, r
); return r
;
279 inline BitSet
operator - (const BitSet
& x
, const BitSet
& y
)
281 BitSet r
; diff(x
, y
, r
); return r
;
284 inline BitSet
operator ~ (const BitSet
& x
)
286 BitSet r
; ::complement(x
, r
); return r
;
291 inline void BitSet::operator &= (const BitSet
& y
)
293 and(*this, y
, *this);
296 inline void BitSet::operator |= (const BitSet
& y
)
301 inline void BitSet::operator ^= (const BitSet
& y
)
303 xor(*this, y
, *this);
306 inline void BitSet::operator -= (const BitSet
& y
)
308 diff(*this, y
, *this);
312 inline void BitSet::complement()
314 ::complement(*this, *this);
317 inline int BitSet::virtual_bit() const
322 inline int BitSet::first(int b
) const
327 inline int BitSet::test(int p
) const
329 if (p
< 0) error("Illegal bit index");
330 int index
= BitSet_index(p
);
331 return (index
>= rep
->len
)? rep
->virt
:
332 ((rep
->s
[index
] & (1 << BitSet_pos(p
))) != 0);
336 inline void BitSet::clear()
338 if (rep
->len
> 0) bzero(rep
->s
, rep
->sz
* sizeof(short));
339 rep
->len
= rep
->virt
= 0;
342 inline void BitSet::set()
344 rep
= BitSetalloc(rep
, 0, 0, 1, 0);
347 inline BitSetBit::BitSetBit(const BitSetBit
& b
) :src(b
.src
), pos(b
.pos
) {}
349 inline BitSetBit::BitSetBit(BitSet
* v
, int p
)
354 inline BitSetBit::~BitSetBit() {}
356 inline BitSetBit::operator int()
358 return src
->test(pos
);
361 inline int BitSetBit::operator = (int b
)
363 if (b
) src
->set(pos
); else src
->clear(pos
); return b
;
366 inline int BitSetBit::operator == (int b
)
368 return src
->test(pos
) == b
;
371 inline int BitSetBit::operator != (int b
)
373 return src
->test(pos
) != b
;
376 inline BitSetBit
BitSet::operator [] (int i
)
378 if (i
< 0) error("illegal bit index");
379 return BitSetBit(this, i
);