@@ -575,6 +575,13 @@ public struct Set<Element : Hashable> :
575
575
public mutating func intersectInPlace<
576
576
S : SequenceType where S.Generator.Element == Element
577
577
>(sequence: S) {
578
+ if let other = sequence as? Set<Element> {
579
+ // removeAll() is fast, prefer using it when possible
580
+ if other.isEmpty {
581
+ removeAll()
582
+ }
583
+ }
584
+
578
585
// Because `intersect` needs to both modify and iterate over
579
586
// the left-hand side, the index may become invalidated during
580
587
// traversal so an intermediate set must be created.
@@ -3394,26 +3401,27 @@ internal enum _Variant${Self}Storage<${TypeParametersDecl}> : _HashStorageType {
3394
3401
}
3395
3402
3396
3403
internal mutating func nativeRemoveAll() {
3397
- var nativeStorage = native
3398
-
3399
- // FIXME(performance): if the storage is non-uniquely referenced, we
3400
- // shouldn’t be copying the elements into new storage and then immediately
3401
- // deleting the elements. We should detect that the storage is not uniquely
3402
- // referenced and allocate new empty storage of appropriate capacity.
3403
3404
3404
3405
// We have already checked for the empty dictionary case, so we will always
3405
3406
// mutating the dictionary storage. Request unique storage.
3406
- let (reallocated, _) = ensureUniqueNativeStorage(nativeStorage.capacity)
3407
- if reallocated {
3408
- nativeStorage = native
3409
- }
3410
3407
3411
- for var b = 0; b != nativeStorage.capacity; ++b {
3412
- if nativeStorage.isInitializedEntry(b) {
3413
- nativeStorage.destroyEntryAt(b)
3408
+ if !isUniquelyReferenced() {
3409
+ switch self {
3410
+ case .Native(let owner):
3411
+ owner.deinitializeHeapBufferBridged()
3412
+ case .Cocoa:
3413
+ _sanityCheckFailure("internal error: not backed by native storage")
3414
+ }
3415
+ let newNativeOwner = NativeStorageOwner(minimumCapacity: native.capacity)
3416
+ self = .Native(newNativeOwner)
3417
+ } else {
3418
+ for b in 0..<native.capacity {
3419
+ if native.isInitializedEntry(b) {
3420
+ native.destroyEntryAt(b)
3421
+ }
3414
3422
}
3415
3423
}
3416
- nativeStorage .count = 0
3424
+ native .count = 0
3417
3425
}
3418
3426
3419
3427
internal mutating func removeAll(keepCapacity keepCapacity: Bool) {
0 commit comments