@@ -19,6 +19,20 @@ use bitslice::{bitwise, Union, Subtract, Intersect};
1919use indexed_vec:: Idx ;
2020use rustc_serialize;
2121
22+ /// This is implemented by all the index sets so that IdxSet::union() can be
23+ /// passed any type of index set.
24+ pub trait UnionIntoIdxSet < T : Idx > {
25+ // Performs `other = other | self`.
26+ fn union_into ( & self , other : & mut IdxSet < T > ) -> bool ;
27+ }
28+
29+ /// This is implemented by all the index sets so that IdxSet::subtract() can be
30+ /// passed any type of index set.
31+ pub trait SubtractFromIdxSet < T : Idx > {
32+ // Performs `other = other - self`.
33+ fn subtract_from ( & self , other : & mut IdxSet < T > ) -> bool ;
34+ }
35+
2236/// Represents a set of some element type E, where each E is identified by some
2337/// unique index type `T`.
2438///
@@ -68,34 +82,34 @@ impl<T: Idx> fmt::Debug for IdxSet<T> {
6882}
6983
7084impl < T : Idx > IdxSet < T > {
71- fn new ( init : Word , universe_size : usize ) -> Self {
72- let num_words = ( universe_size + ( BITS_PER_WORD - 1 ) ) / BITS_PER_WORD ;
85+ fn new ( init : Word , domain_size : usize ) -> Self {
86+ let num_words = ( domain_size + ( BITS_PER_WORD - 1 ) ) / BITS_PER_WORD ;
7387 IdxSet {
7488 _pd : Default :: default ( ) ,
7589 bits : vec ! [ init; num_words] ,
7690 }
7791 }
7892
79- /// Creates set holding every element whose index falls in range 0..universe_size .
80- pub fn new_filled ( universe_size : usize ) -> Self {
81- let mut result = Self :: new ( !0 , universe_size ) ;
82- result. trim_to ( universe_size ) ;
93+ /// Creates set holding every element whose index falls in range 0..domain_size .
94+ pub fn new_filled ( domain_size : usize ) -> Self {
95+ let mut result = Self :: new ( !0 , domain_size ) ;
96+ result. trim_to ( domain_size ) ;
8397 result
8498 }
8599
86100 /// Creates set holding no elements.
87- pub fn new_empty ( universe_size : usize ) -> Self {
88- Self :: new ( 0 , universe_size )
101+ pub fn new_empty ( domain_size : usize ) -> Self {
102+ Self :: new ( 0 , domain_size )
89103 }
90104
91105 /// Duplicates as a hybrid set.
92106 pub fn to_hybrid ( & self ) -> HybridIdxSet < T > {
93- // This universe_size may be slightly larger than the one specified
107+ // This domain_size may be slightly larger than the one specified
94108 // upon creation, due to rounding up to a whole word. That's ok.
95- let universe_size = self . bits . len ( ) * BITS_PER_WORD ;
109+ let domain_size = self . bits . len ( ) * BITS_PER_WORD ;
96110
97111 // Note: we currently don't bother trying to make a Sparse set.
98- HybridIdxSet :: Dense ( self . to_owned ( ) , universe_size )
112+ HybridIdxSet :: Dense ( self . to_owned ( ) , domain_size )
99113 }
100114
101115 /// Removes all elements
@@ -105,29 +119,29 @@ impl<T: Idx> IdxSet<T> {
105119 }
106120 }
107121
108- /// Sets all elements up to `universe_size `
109- pub fn set_up_to ( & mut self , universe_size : usize ) {
122+ /// Sets all elements up to `domain_size `
123+ pub fn set_up_to ( & mut self , domain_size : usize ) {
110124 for b in & mut self . bits {
111125 * b = !0 ;
112126 }
113- self . trim_to ( universe_size ) ;
127+ self . trim_to ( domain_size ) ;
114128 }
115129
116- /// Clear all elements above `universe_size `.
117- fn trim_to ( & mut self , universe_size : usize ) {
130+ /// Clear all elements above `domain_size `.
131+ fn trim_to ( & mut self , domain_size : usize ) {
118132 // `trim_block` is the first block where some bits have
119133 // to be cleared.
120- let trim_block = universe_size / BITS_PER_WORD ;
134+ let trim_block = domain_size / BITS_PER_WORD ;
121135
122136 // all the blocks above it have to be completely cleared.
123137 if trim_block < self . bits . len ( ) {
124138 for b in & mut self . bits [ trim_block+1 ..] {
125139 * b = 0 ;
126140 }
127141
128- // at that block, the `universe_size % BITS_PER_WORD` lsbs
142+ // at that block, the `domain_size % BITS_PER_WORD` LSBs
129143 // should remain.
130- let remaining_bits = universe_size % BITS_PER_WORD ;
144+ let remaining_bits = domain_size % BITS_PER_WORD ;
131145 let mask = ( 1 <<remaining_bits) -1 ;
132146 self . bits [ trim_block] &= mask;
133147 }
@@ -164,48 +178,14 @@ impl<T: Idx> IdxSet<T> {
164178
165179 /// Set `self = self | other` and return true if `self` changed
166180 /// (i.e., if new bits were added).
167- pub fn union ( & mut self , other : & IdxSet < T > ) -> bool {
168- bitwise ( self . words_mut ( ) , other. words ( ) , & Union )
169- }
170-
171- /// Like `union()`, but takes a `SparseIdxSet` argument.
172- fn union_sparse ( & mut self , other : & SparseIdxSet < T > ) -> bool {
173- let mut changed = false ;
174- for elem in other. iter ( ) {
175- changed |= self . add ( & elem) ;
176- }
177- changed
178- }
179-
180- /// Like `union()`, but takes a `HybridIdxSet` argument.
181- pub fn union_hybrid ( & mut self , other : & HybridIdxSet < T > ) -> bool {
182- match other {
183- HybridIdxSet :: Sparse ( sparse, _) => self . union_sparse ( sparse) ,
184- HybridIdxSet :: Dense ( dense, _) => self . union ( dense) ,
185- }
181+ pub fn union ( & mut self , other : & impl UnionIntoIdxSet < T > ) -> bool {
182+ other. union_into ( self )
186183 }
187184
188185 /// Set `self = self - other` and return true if `self` changed.
189186 /// (i.e., if any bits were removed).
190- pub fn subtract ( & mut self , other : & IdxSet < T > ) -> bool {
191- bitwise ( self . words_mut ( ) , other. words ( ) , & Subtract )
192- }
193-
194- /// Like `subtract()`, but takes a `SparseIdxSet` argument.
195- fn subtract_sparse ( & mut self , other : & SparseIdxSet < T > ) -> bool {
196- let mut changed = false ;
197- for elem in other. iter ( ) {
198- changed |= self . remove ( & elem) ;
199- }
200- changed
201- }
202-
203- /// Like `subtract()`, but takes a `HybridIdxSet` argument.
204- pub fn subtract_hybrid ( & mut self , other : & HybridIdxSet < T > ) -> bool {
205- match other {
206- HybridIdxSet :: Sparse ( sparse, _) => self . subtract_sparse ( sparse) ,
207- HybridIdxSet :: Dense ( dense, _) => self . subtract ( dense) ,
208- }
187+ pub fn subtract ( & mut self , other : & impl SubtractFromIdxSet < T > ) -> bool {
188+ other. subtract_from ( self )
209189 }
210190
211191 /// Set `self = self & other` and return true if `self` changed.
@@ -223,6 +203,18 @@ impl<T: Idx> IdxSet<T> {
223203 }
224204}
225205
206+ impl < T : Idx > UnionIntoIdxSet < T > for IdxSet < T > {
207+ fn union_into ( & self , other : & mut IdxSet < T > ) -> bool {
208+ bitwise ( other. words_mut ( ) , self . words ( ) , & Union )
209+ }
210+ }
211+
212+ impl < T : Idx > SubtractFromIdxSet < T > for IdxSet < T > {
213+ fn subtract_from ( & self , other : & mut IdxSet < T > ) -> bool {
214+ bitwise ( other. words_mut ( ) , self . words ( ) , & Subtract )
215+ }
216+ }
217+
226218pub struct Iter < ' a , T : Idx > {
227219 cur : Option < ( Word , usize ) > ,
228220 iter : iter:: Enumerate < slice:: Iter < ' a , Word > > ,
@@ -293,8 +285,8 @@ impl<T: Idx> SparseIdxSet<T> {
293285 }
294286 }
295287
296- fn to_dense ( & self , universe_size : usize ) -> IdxSet < T > {
297- let mut dense = IdxSet :: new_empty ( universe_size ) ;
288+ fn to_dense ( & self , domain_size : usize ) -> IdxSet < T > {
289+ let mut dense = IdxSet :: new_empty ( domain_size ) ;
298290 for elem in self . 0 . iter ( ) {
299291 dense. add ( elem) ;
300292 }
@@ -308,6 +300,26 @@ impl<T: Idx> SparseIdxSet<T> {
308300 }
309301}
310302
303+ impl < T : Idx > UnionIntoIdxSet < T > for SparseIdxSet < T > {
304+ fn union_into ( & self , other : & mut IdxSet < T > ) -> bool {
305+ let mut changed = false ;
306+ for elem in self . iter ( ) {
307+ changed |= other. add ( & elem) ;
308+ }
309+ changed
310+ }
311+ }
312+
313+ impl < T : Idx > SubtractFromIdxSet < T > for SparseIdxSet < T > {
314+ fn subtract_from ( & self , other : & mut IdxSet < T > ) -> bool {
315+ let mut changed = false ;
316+ for elem in self . iter ( ) {
317+ changed |= other. remove ( & elem) ;
318+ }
319+ changed
320+ }
321+ }
322+
311323pub struct SparseIter < ' a , T : Idx > {
312324 iter : slice:: Iter < ' a , T > ,
313325}
@@ -323,28 +335,24 @@ impl<'a, T: Idx> Iterator for SparseIter<'a, T> {
323335/// Like IdxSet, but with a hybrid representation: sparse when there are few
324336/// elements in the set, but dense when there are many. It's especially
325337/// efficient for sets that typically have a small number of elements, but a
326- /// large `universe_size `, and are cleared frequently.
338+ /// large `domain_size `, and are cleared frequently.
327339#[ derive( Clone , Debug ) ]
328340pub enum HybridIdxSet < T : Idx > {
329341 Sparse ( SparseIdxSet < T > , usize ) ,
330342 Dense ( IdxSet < T > , usize ) ,
331343}
332344
333345impl < T : Idx > HybridIdxSet < T > {
334- pub fn new_empty ( universe_size : usize ) -> Self {
335- HybridIdxSet :: Sparse ( SparseIdxSet :: new ( ) , universe_size )
346+ pub fn new_empty ( domain_size : usize ) -> Self {
347+ HybridIdxSet :: Sparse ( SparseIdxSet :: new ( ) , domain_size )
336348 }
337349
338- fn universe_size ( & mut self ) -> usize {
339- match * self {
350+ pub fn clear ( & mut self ) {
351+ let domain_size = match * self {
340352 HybridIdxSet :: Sparse ( _, size) => size,
341353 HybridIdxSet :: Dense ( _, size) => size,
342- }
343- }
344-
345- pub fn clear ( & mut self ) {
346- let universe_size = self . universe_size ( ) ;
347- * self = HybridIdxSet :: new_empty ( universe_size) ;
354+ } ;
355+ * self = HybridIdxSet :: new_empty ( domain_size) ;
348356 }
349357
350358 /// Returns true iff set `self` contains `elem`.
@@ -374,11 +382,11 @@ impl<T: Idx> HybridIdxSet<T> {
374382 // appease the borrow checker.
375383 let dummy = HybridIdxSet :: Sparse ( SparseIdxSet :: new ( ) , 0 ) ;
376384 match mem:: replace ( self , dummy) {
377- HybridIdxSet :: Sparse ( sparse, universe_size ) => {
378- let mut dense = sparse. to_dense ( universe_size ) ;
385+ HybridIdxSet :: Sparse ( sparse, domain_size ) => {
386+ let mut dense = sparse. to_dense ( domain_size ) ;
379387 let changed = dense. add ( elem) ;
380388 assert ! ( changed) ;
381- mem:: replace ( self , HybridIdxSet :: Dense ( dense, universe_size ) ) ;
389+ mem:: replace ( self , HybridIdxSet :: Dense ( dense, domain_size ) ) ;
382390 changed
383391 }
384392 _ => panic ! ( "impossible" ) ,
@@ -401,7 +409,7 @@ impl<T: Idx> HybridIdxSet<T> {
401409 /// Converts to a dense set, consuming itself in the process.
402410 pub fn to_dense ( self ) -> IdxSet < T > {
403411 match self {
404- HybridIdxSet :: Sparse ( sparse, universe_size ) => sparse. to_dense ( universe_size ) ,
412+ HybridIdxSet :: Sparse ( sparse, domain_size ) => sparse. to_dense ( domain_size ) ,
405413 HybridIdxSet :: Dense ( dense, _) => dense,
406414 }
407415 }
@@ -415,6 +423,24 @@ impl<T: Idx> HybridIdxSet<T> {
415423 }
416424}
417425
426+ impl < T : Idx > UnionIntoIdxSet < T > for HybridIdxSet < T > {
427+ fn union_into ( & self , other : & mut IdxSet < T > ) -> bool {
428+ match self {
429+ HybridIdxSet :: Sparse ( sparse, _) => sparse. union_into ( other) ,
430+ HybridIdxSet :: Dense ( dense, _) => dense. union_into ( other) ,
431+ }
432+ }
433+ }
434+
435+ impl < T : Idx > SubtractFromIdxSet < T > for HybridIdxSet < T > {
436+ fn subtract_from ( & self , other : & mut IdxSet < T > ) -> bool {
437+ match self {
438+ HybridIdxSet :: Sparse ( sparse, _) => sparse. subtract_from ( other) ,
439+ HybridIdxSet :: Dense ( dense, _) => dense. subtract_from ( other) ,
440+ }
441+ }
442+ }
443+
418444pub enum HybridIter < ' a , T : Idx > {
419445 Sparse ( SparseIter < ' a , T > ) ,
420446 Dense ( Iter < ' a , T > ) ,
0 commit comments