@@ -36,7 +36,7 @@ trait Set[A] extends Iterable[A]
36
36
{
37
37
override def companion : GenericCompanion [Set ] = Set
38
38
39
-
39
+
40
40
/** Returns this $coll as an immutable set, perhaps accepting a
41
41
* wider range of elements. Since it already is an
42
42
* immutable set, it will only be rebuilt if the underlying structure
@@ -53,7 +53,7 @@ trait Set[A] extends Iterable[A]
53
53
foreach(sb += _)
54
54
sb.result()
55
55
}
56
-
56
+
57
57
override def seq : Set [A ] = this
58
58
protected override def parCombiner = ParSet .newCombiner[A ] // if `immutable.SetLike` gets introduced, please move this there!
59
59
}
@@ -100,6 +100,29 @@ object Set extends ImmutableSetFactory[Set] {
100
100
}
101
101
private [collection] def emptyInstance : Set [Any ] = EmptySet
102
102
103
+ @ SerialVersionUID (3L )
104
+ private abstract class SetNIterator [A ](n : Int ) extends AbstractIterator [A ] with Serializable {
105
+ private [this ] var current = 0
106
+ private [this ] var remainder = n
107
+ def hasNext = remainder > 0
108
+ def apply (i : Int ): A
109
+ def next (): A =
110
+ if (hasNext) {
111
+ val r = apply(current)
112
+ current += 1
113
+ remainder -= 1
114
+ r
115
+ } else Iterator .empty.next()
116
+
117
+ override def drop (n : Int ): Iterator [A ] = {
118
+ if (n > 0 ) {
119
+ current += n
120
+ remainder = Math .max(0 , remainder - n)
121
+ }
122
+ this
123
+ }
124
+ }
125
+
103
126
/** An optimized representation for immutable sets of size 1 */
104
127
@ SerialVersionUID (1233385750652442003L )
105
128
class Set1 [A ] private [collection] (elem1 : A ) extends AbstractSet [A ] with Set [A ] with Serializable {
@@ -113,7 +136,7 @@ object Set extends ImmutableSetFactory[Set] {
113
136
if (elem == elem1) Set .empty
114
137
else this
115
138
def iterator : Iterator [A ] =
116
- Iterator (elem1)
139
+ Iterator .single (elem1)
117
140
override def foreach [U ](f : A => U ): Unit = {
118
141
f(elem1)
119
142
}
@@ -123,6 +146,8 @@ object Set extends ImmutableSetFactory[Set] {
123
146
override def forall (@ deprecatedName(' f ) p : A => Boolean ): Boolean = {
124
147
p(elem1)
125
148
}
149
+ override private [scala] def filterImpl (pred : A => Boolean , isFlipped : Boolean ): Set [A ] =
150
+ if (pred(elem1) != isFlipped) this else Set .empty
126
151
override def find (@ deprecatedName(' f ) p : A => Boolean ): Option [A ] = {
127
152
if (p(elem1)) Some (elem1)
128
153
else None
@@ -147,8 +172,11 @@ object Set extends ImmutableSetFactory[Set] {
147
172
if (elem == elem1) new Set1 (elem2)
148
173
else if (elem == elem2) new Set1 (elem1)
149
174
else this
150
- def iterator : Iterator [A ] =
151
- Iterator (elem1, elem2)
175
+ def iterator : Iterator [A ] = new SetNIterator [A ](size) {
176
+ def apply (i : Int ) = getElem(i)
177
+ }
178
+ private def getElem (i : Int ) = i match { case 0 => elem1 case 1 => elem2 }
179
+
152
180
override def foreach [U ](f : A => U ): Unit = {
153
181
f(elem1); f(elem2)
154
182
}
@@ -158,6 +186,18 @@ object Set extends ImmutableSetFactory[Set] {
158
186
override def forall (@ deprecatedName(' f ) p : A => Boolean ): Boolean = {
159
187
p(elem1) && p(elem2)
160
188
}
189
+ override private [scala] def filterImpl (pred : A => Boolean , isFlipped : Boolean ): Set [A ] = {
190
+ var r1 : A = null .asInstanceOf [A ]
191
+ var n = 0
192
+ if (pred(elem1) != isFlipped) { r1 = elem1; n += 1 }
193
+ if (pred(elem2) != isFlipped) { if (n == 0 ) r1 = elem2; n += 1 }
194
+
195
+ n match {
196
+ case 0 => Set .empty
197
+ case 1 => new Set1 (r1)
198
+ case 2 => this
199
+ }
200
+ }
161
201
override def find (@ deprecatedName(' f ) p : A => Boolean ): Option [A ] = {
162
202
if (p(elem1)) Some (elem1)
163
203
else if (p(elem2)) Some (elem2)
@@ -184,8 +224,11 @@ object Set extends ImmutableSetFactory[Set] {
184
224
else if (elem == elem2) new Set2 (elem1, elem3)
185
225
else if (elem == elem3) new Set2 (elem1, elem2)
186
226
else this
187
- def iterator : Iterator [A ] =
188
- Iterator (elem1, elem2, elem3)
227
+ def iterator : Iterator [A ] = new SetNIterator [A ](size) {
228
+ def apply (i : Int ) = getElem(i)
229
+ }
230
+ private def getElem (i : Int ) = i match { case 0 => elem1 case 1 => elem2 case 2 => elem3 }
231
+
189
232
override def foreach [U ](f : A => U ): Unit = {
190
233
f(elem1); f(elem2); f(elem3)
191
234
}
@@ -195,6 +238,20 @@ object Set extends ImmutableSetFactory[Set] {
195
238
override def forall (@ deprecatedName(' f ) p : A => Boolean ): Boolean = {
196
239
p(elem1) && p(elem2) && p(elem3)
197
240
}
241
+ override private [scala] def filterImpl (pred : A => Boolean , isFlipped : Boolean ): Set [A ] = {
242
+ var r1, r2 : A = null .asInstanceOf [A ]
243
+ var n = 0
244
+ if (pred(elem1) != isFlipped) { r1 = elem1; n += 1 }
245
+ if (pred(elem2) != isFlipped) { if (n == 0 ) r1 = elem2 else r2 = elem2; n += 1 }
246
+ if (pred(elem3) != isFlipped) { if (n == 0 ) r1 = elem3 else if (n == 1 ) r2 = elem3; n += 1 }
247
+
248
+ n match {
249
+ case 0 => Set .empty
250
+ case 1 => new Set1 (r1)
251
+ case 2 => new Set2 (r1, r2)
252
+ case 3 => this
253
+ }
254
+ }
198
255
override def find (@ deprecatedName(' f ) p : A => Boolean ): Option [A ] = {
199
256
if (p(elem1)) Some (elem1)
200
257
else if (p(elem2)) Some (elem2)
@@ -223,8 +280,11 @@ object Set extends ImmutableSetFactory[Set] {
223
280
else if (elem == elem3) new Set3 (elem1, elem2, elem4)
224
281
else if (elem == elem4) new Set3 (elem1, elem2, elem3)
225
282
else this
226
- def iterator : Iterator [A ] =
227
- Iterator (elem1, elem2, elem3, elem4)
283
+ def iterator : Iterator [A ] = new SetNIterator [A ](size) {
284
+ def apply (i : Int ) = getElem(i)
285
+ }
286
+ private def getElem (i : Int ) = i match { case 0 => elem1 case 1 => elem2 case 2 => elem3 case 3 => elem4 }
287
+
228
288
override def foreach [U ](f : A => U ): Unit = {
229
289
f(elem1); f(elem2); f(elem3); f(elem4)
230
290
}
@@ -234,6 +294,23 @@ object Set extends ImmutableSetFactory[Set] {
234
294
override def forall (@ deprecatedName(' f ) p : A => Boolean ): Boolean = {
235
295
p(elem1) && p(elem2) && p(elem3) && p(elem4)
236
296
}
297
+ override private [scala] def filterImpl (pred : A => Boolean , isFlipped : Boolean ): Set [A ] = {
298
+ var r1, r2, r3 : A = null .asInstanceOf [A ]
299
+ var n = 0
300
+ if (pred(elem1) != isFlipped) { r1 = elem1; n += 1 }
301
+ if (pred(elem2) != isFlipped) { if (n == 0 ) r1 = elem2 else r2 = elem2; n += 1 }
302
+ if (pred(elem3) != isFlipped) { if (n == 0 ) r1 = elem3 else if (n == 1 ) r2 = elem3 else r3 = elem3; n += 1 }
303
+ if (pred(elem4) != isFlipped) { if (n == 0 ) r1 = elem4 else if (n == 1 ) r2 = elem4 else if (n == 2 ) r3 = elem4; n += 1 }
304
+
305
+ n match {
306
+ case 0 => Set .empty
307
+ case 1 => new Set1 (r1)
308
+ case 2 => new Set2 (r1, r2)
309
+ case 3 => new Set3 (r1, r2, r3)
310
+ case 4 => this
311
+ }
312
+ }
313
+
237
314
override def find (@ deprecatedName(' f ) p : A => Boolean ): Option [A ] = {
238
315
if (p(elem1)) Some (elem1)
239
316
else if (p(elem2)) Some (elem2)
0 commit comments