Collection
声明
protocol Collection<Element> : Sequence
概述
集合在整个标准库中被广泛使用。当您使用数组、字典和其他集合时,您将从 Collection
协议声明和实现的操作中受益。除了集合从 Sequence
协议继承的操作之外,您还可以访问依赖于访问集合中特定位置的元素的方法。
例如,如果您只想打印字符串中的第一个单词,您可以搜索第一个空格的索引,然后创建一个直到该位置的子字符串。
let text = "Buffalo buffalo buffalo buffalo."
if let firstSpace = text.firstIndex(of: " ") {
print(text[..<firstSpace])
}
// Prints "Buffalo"
firstSpace
常量是text
字符串的索引——字符串中第一个空格的位置。您可以将索引存储在变量中,并将它们传递给集合算法或稍后使用它们来访问相应的元素。在上面的示例中,firstSpace
用于提取包含直到该索引的元素的前缀。
访问单个元素
您可以使用集合的endIndex
属性以外的任何有效索引,通过其下标访问集合的元素。此属性是一个“past the end” 索引,它与集合的任何元素都不对应。
下面是一个通过下标访问字符串中第一个字符的示例:
let firstChar = text[text.startIndex]
print(firstChar)
// Prints "B"
Collection
协议声明并提供了许多操作的默认实现,这些操作依赖于可通过其下标访问的元素。例如,您还可以使用first
属性访问text
的第一个字符,该属性具有集合的第一个元素的值,或者如果集合为空,则为nil
。
print(text.first)
// Prints "Optional("B")"
您只能将有效索引传递给集合操作。您可以通过从集合的startIndex
属性开始并查找直到(包括)endIndex
属性的每个后继来找到一组完整的集合有效索引。 Index
类型的所有其他值,例如不同集合的startIndex
属性,都是此集合的无效索引。
由于变异操作,保存的索引可能会变得无效。有关可变集合中索引失效的更多信息,请参阅MutableCollection
和RangeReplaceableCollection
协议以及您正在使用的特定类型的参考。
访问集合的切片
您可以通过其范围下标或调用 prefix(while:)
或 suffix(_:)
等方法来访问集合的切片。集合的切片可以包含零个或多个原始集合的元素,并共享原始集合的语义。
下面的示例通过使用prefix(while:)
方法创建firstWord
常量来获取text
字符串的一部分。
let firstWord = text.prefix(while: { $0 != " " })
print(firstWord)
// Prints "Buffalo"
您可以使用字符串的范围下标检索相同的切片,该下标采用范围表达式。
if let firstSpace = text.firstIndex(of: " ") {
print(text[..<firstSpace]
// Prints "Buffalo"
}
text
的检索切片在每种情况下都是等效的。
切片股票指数
集合及其切片共享相同的索引。集合的元素位于切片中与基本集合中相同的索引下,只要集合和切片自切片创建以来都没有发生突变。
例如,假设您有一个数组,其中包含一个会话期间每个类的缺勤次数。
var absences = [0, 2, 0, 4, 0, 3, 1, 0]
你的任务是找出下半场缺勤最多的一天。要查找相关日期的索引,请执行以下步骤:
-
创建包含后半天的
absences
数组的切片。 -
使用
max(by:)
方法确定缺勤次数最多的一天的索引。 -
使用在步骤 2 中找到的原始
absences
数组上的索引打印结果。
以下是这些步骤的实现:
let secondHalf = absences.suffix(absences.count / 2)
if let i = secondHalf.indices.max(by: { secondHalf[$0] < secondHalf[$1] }) {
print("Highest second-half absences: \(absences[i])")
}
// Prints "Highest second-half absences: 3"
切片继承集合语义
切片继承其基本集合的值或引用语义。也就是说,当使用具有值语义的可变集合的切片(例如数组)时,改变原始集合会触发该集合的副本,并且不会影响切片的内容。
例如,如果您将 absences
数组的最后一个元素从 0
更新为 2
,则 secondHalf
切片保持不变。
absences[7] = 2
print(absences)
// Prints "[0, 2, 0, 4, 0, 3, 1, 2]"
print(secondHalf)
// Prints "[0, 3, 1, 0]"
遍历集合
尽管可以在遍历序列时使用它,但可以保证集合是 multipass
:任何元素都可以通过保存其索引来重复访问。此外,集合的索引构成了集合元素位置的有限范围。所有集合都是有限的这一事实保证了许多序列操作的安全性,例如使用contains(_:)
方法来测试集合是否包含元素。
按位置迭代集合的元素会产生相同的元素,其顺序与使用其迭代器迭代该集合的顺序相同。此示例演示了字符串的 characters
视图以相同的顺序返回相同的字符,无论是迭代视图的索引还是视图本身。
let word = "Swift"
for character in word {
print(character)
}
// Prints "S"
// Prints "w"
// Prints "i"
// Prints "f"
// Prints "t"
for i in word.indices {
print(word[i])
}
// Prints "S"
// Prints "w"
// Prints "i"
// Prints "f"
// Prints "t"
符合收集协议
如果您创建一个可以提供对其元素的重复访问的自定义序列,请确保其类型符合Collection
协议,以便为序列和集合操作提供更有用和更有效的接口。要将Collection
一致性添加到您的类型,您必须至少声明以下要求:
-
startIndex
和endIndex
属性 -
至少提供对类型元素的只读访问权限的下标
-
index(after:)
将索引推进到集合中的方法
预期表现
符合 Collection
的类型应提供 startIndex
和 endIndex
属性和对元素的下标访问,作为 O(1) 操作。不能保证这种性能的类型必须记录偏离,因为许多收集操作依赖于 O(1) 下标性能来保证它们自己的性能。
某些集合操作的性能取决于集合提供的索引类型。例如,可以在 O(1) 时间内测量两个索引之间的距离的随机访问集合可以在 O(1) 时间内计算其count
属性。相反,由于前向或双向集合必须遍历整个集合以计算包含元素的数量,因此访问其count
属性是 O(n
) 操作。
可用版本
相关用法
- Swift CollectionDifference firstIndex(of:)用法及代码示例
- Swift Collection prefix(upTo:)用法及代码示例
- Swift CollectionOfOne contains(_:)用法及代码示例
- Swift Collection first用法及代码示例
- Swift CollectionOfOne compactMap(_:)用法及代码示例
- Swift CollectionDifference contains(where:)用法及代码示例
- Swift CollectionOfOne last(where:)用法及代码示例
- Swift Collection dropLast(_:)用法及代码示例
- Swift CollectionDifference forEach(_:)用法及代码示例
- Swift CollectionDifference firstIndex(where:)用法及代码示例
- Swift CollectionDifference prefix(_:)用法及代码示例
- Swift CollectionOfOne firstIndex(of:)用法及代码示例
- Swift CollectionDifference randomElement()用法及代码示例
- Swift CollectionDifference endIndex用法及代码示例
- Swift CollectionDifference starts(with:)用法及代码示例
- Swift CollectionOfOne subscript(_:)用法及代码示例
- Swift Collection index(_:offsetBy:)用法及代码示例
- Swift Collection map(_:)用法及代码示例
- Swift CollectionOfOne shuffled()用法及代码示例
- Swift CollectionDifference sorted(by:)用法及代码示例
- Swift CollectionOfOne reversed()用法及代码示例
- Swift CollectionDifference randomElement(using:)用法及代码示例
- Swift Collection subscript(_:)用法及代码示例
- Swift CollectionOfOne prefix(through:)用法及代码示例
- Swift CollectionOfOne contains(where:)用法及代码示例
注:本文由纯净天空筛选整理自apple.com大神的英文原创作品 Collection。非经特殊声明,原始代码版权归原作者所有,本译文未经允许或授权,请勿转载或复制。