当前位置: 首页>>代码示例 >>用法及示例精选 >>正文


Swift Set用法及代码示例


结构

Set

独特元素的无序集合。

声明

@frozen struct Set<Element> where Element : Hashable

概述

当您需要有效地测试成员资格并且您不关心集合中元素的顺序,或者当您需要确保每个元素在集合中只出现一次时,您可以使用集合而不是数组。

您可以使用符合Hashable 协议的任何元素类型创建集合。默认情况下,标准库中的大多数类型都是可散列的,包括字符串、数字和布尔类型、没有关联值的枚举情况,甚至是集合本身。

Swift 让创建一个新集合就像创建一个新数组一样容易。只需将数组文字分配给指定 Set 类型的变量或常量。


let ingredients: Set = ["cocoa beans", "sugar", "cocoa butter", "salt"]
if ingredients.contains("sugar") {
    print("No thanks, too sweet.")
}
// Prints "No thanks, too sweet."

设置操作

集合提供了一套数学集合操作。例如,您可以有效地测试一个集合的元素成员资格或检查它与另一个集合的交集:

  • 使用contains(_:) 方法测试集合是否包含特定元素。

  • 使用 “equal to” 运算符 (==) 来测试两个集合是否包含相同的元素。

  • 使用isSubset(of:) 方法测试一个集合是否包含另一个集合或序列的所有元素。

  • 使用isSuperset(of:) 方法测试一个集合的所有元素是否包含在另一个集合或序列中。

  • 使用isStrictSubset(of:)isStrictSuperset(of:) 方法来测试一个集合是否是另一个集合的子集或超集,但不等于另一个集合。

  • 使用isDisjoint(with:) 方法测试一个集合是否与另一个集合有任何共同的元素。

您还可以组合、排除或减去两个集合的元素:

  • 使用union(_:) 方法创建一个包含一个集合的元素和另一个集合或序列的新集合。

  • 使用intersection(_:) 方法创建一个新集合,其中仅包含一个集合和另一个集合或序列共有的元素。

  • 使用symmetricDifference(_:) 方法创建一个新集合,其中包含在一个集合或另一个集合或序列中的元素,但不能同时在两者中。

  • 使用subtracting(_:) 方法创建一个新集合,其中包含一个集合中不在另一个集合或序列中的元素。

您可以使用这些方法的变异对应项来修改集合:formUnion(_:)formIntersection(_:)formSymmetricDifference(_:)subtract(_:)

集合操作不限于与其他集合一起使用。相反,您可以对另一个集合、数组或任何其他序列类型执行集合操作。


var primes: Set = [2, 3, 5, 7]


// Tests whether primes is a subset of a Range<Int>
print(primes.isSubset(of: 0..<10))
// Prints "true"


// Performs an intersection with an Array<Int>
let favoriteNumbers = [5, 7, 15, 21]
print(primes.intersection(favoriteNumbers))
// Prints "[5, 7]"

序列和集合操作

除了 Set 类型的集合操作之外,您还可以对集合使用任何非可变序列或集合方法。


if primes.isEmpty {
    print("No primes!")
} else {
    print("We have \(primes.count) primes.")
}
// Prints "We have 4 primes."


let primesSum = primes.reduce(0, +)
// 'primesSum' == 17


let primeStrings = primes.sorted().map(String.init)
// 'primeStrings' == ["2", "3", "5", "7"]

您可以使用 for - in 循环遍历集合的无序元素。


for number in primes {
    print(number)
}
// Prints "5"
// Prints "7"
// Prints "2"
// Prints "3"

许多序列和集合操作返回一个数组或 type-erasing 集合包装器而不是集合。要恢复有效的集合操作,请从结果中创建一个新集合。


let primesStrings = primes.map(String.init)
// 'primesStrings' is of type Array<String>
let primesStringsSet = Set(primes.map(String.init))
// 'primesStringsSet' is of type Set<String>

Set 和 NSSet 之间的桥接

您可以使用as 运算符在SetNSSet 之间进行桥接。为了使桥接成为可能,集合的 Element 类型必须是类、@objc 协议(从 Objective-C 导入或标有 @objc 属性的协议)或桥接到 Foundation 的类型类型。

SetNSSet 的桥接总是需要 O(1) 的时间和空间。当集合的Element 类型既不是类也不是@objc 协议时,任何所需的元素桥接都发生在第一次访问每个元素时,因此使用集合内容的第一个操作(例如,成员资格测试) 可以取 O(n)。

NSSetSet 的桥接首先调用集合上的copy(with:) 方法(Objective-C 中的- copyWithZone:)以获取不可变副本,然后执行额外的 Swift 簿记工作,这需要 O(1) 时间。对于已经不可变的NSSet 实例,copy(with:) 在恒定时间内返回相同的集合;否则,复制性能未指定。 NSSetSet 的实例使用相同的 copy-on-write 优化来共享缓冲区,这与 Set 的两个实例共享缓冲区时使用的相同。

可用版本

iOS 8.0+, iPadOS 8.0+, macOS 10.10+, Mac Catalyst 13.0+, tvOS 9.0+, watchOS 2.0+

相关用法


注:本文由纯净天空筛选整理自apple.com大神的英文原创作品 Set。非经特殊声明,原始代码版权归原作者所有,本译文未经允许或授权,请勿转载或复制。