@@ -107,6 +107,16 @@ impl Iteration {
107
107
self . variables . push ( Box :: new ( variable. clone ( ) ) ) ;
108
108
variable
109
109
}
110
+ /// Creates a new named variable associated with the iterative context.
111
+ ///
112
+ /// This variable will not be maintained distinctly, and may advertise tuples as
113
+ /// recent multiple times (perhaps unboundedly many times).
114
+ pub fn variable_indistinct < Tuple : Ord +' static > ( & mut self , name : & str ) -> Variable < Tuple > {
115
+ let mut variable = Variable :: new ( name) ;
116
+ variable. distinct = false ;
117
+ self . variables . push ( Box :: new ( variable. clone ( ) ) ) ;
118
+ variable
119
+ }
110
120
}
111
121
112
122
/// A type that can report on whether it has changed.
@@ -128,6 +138,8 @@ pub trait VariableTrait {
128
138
/// `recent`. This way, across calls to `changed()` all added relations are at some point
129
139
/// in `recent` once and eventually all are in `tuples`.
130
140
pub struct Variable < Tuple : Ord > {
141
+ /// Should the variable be maintained distinctly.
142
+ pub distinct : bool ,
131
143
/// A useful name for the variable.
132
144
pub name : String ,
133
145
/// A list of relations whose union are the accepted tuples.
@@ -242,6 +254,7 @@ impl<Tuple: Ord> Variable<Tuple> {
242
254
impl < Tuple : Ord > Clone for Variable < Tuple > {
243
255
fn clone ( & self ) -> Self {
244
256
Variable {
257
+ distinct : self . distinct ,
245
258
name : self . name . clone ( ) ,
246
259
tuples : self . tuples . clone ( ) ,
247
260
recent : self . recent . clone ( ) ,
@@ -253,6 +266,7 @@ impl<Tuple: Ord> Clone for Variable<Tuple> {
253
266
impl < Tuple : Ord > Variable < Tuple > {
254
267
fn new ( name : & str ) -> Self {
255
268
Variable {
269
+ distinct : true ,
256
270
name : name. to_string ( ) ,
257
271
tuples : Rc :: new ( RefCell :: new ( Vec :: new ( ) . into ( ) ) ) ,
258
272
recent : Rc :: new ( RefCell :: new ( Vec :: new ( ) . into ( ) ) ) ,
@@ -305,12 +319,14 @@ impl<Tuple: Ord> VariableTrait for Variable<Tuple> {
305
319
to_add = to_add. merge ( to_add_more) ;
306
320
}
307
321
// 2b. Restrict `to_add` to tuples not in `self.tuples`.
308
- for batch in self . tuples . borrow ( ) . iter ( ) {
309
- let mut slice = & batch[ ..] ;
310
- to_add. elements . retain ( |x| {
311
- slice = join:: gallop ( slice, |y| y < x) ;
312
- slice. len ( ) == 0 || & slice[ 0 ] != x
313
- } )
322
+ if self . distinct {
323
+ for batch in self . tuples . borrow ( ) . iter ( ) {
324
+ let mut slice = & batch[ ..] ;
325
+ to_add. elements . retain ( |x| {
326
+ slice = join:: gallop ( slice, |y| y < x) ;
327
+ slice. len ( ) == 0 || & slice[ 0 ] != x
328
+ } )
329
+ }
314
330
}
315
331
* self . recent . borrow_mut ( ) = to_add;
316
332
}
0 commit comments