简答:
如果您有 MutableCollection 的变量
键入然后您必须仅使用范围调用下标设置器
和一个具有相同长度的新切片。
某些符合MutableCollection 的类型(例如Array)允许使用不同长度的替换来插入或删除元素,
但一般来说,可变集合不需要允许这样做。
特别是MutableCollection 的默认实现
如果范围和
新切片的长度不同。
更长的答案:
首先注意,你不必实现
public subscript(bounds: Range<Index>) -> MutableSlice<Self>
在您自己的集合中,因为它在
协议扩展。正如可以在该方法的source code 中看到的那样,下标设置器调用了一个
internal func _writeBackMutableSlice()
实现here的函数。
该函数首先从
切片到目标范围,然后验证下标范围和新切片的长度相同:
_precondition(
selfElementIndex == selfElementsEndIndex,
"Cannot replace a slice of a MutableCollection with a slice of a smaller size")
_precondition(
newElementIndex == newElementsEndIndex,
"Cannot replace a slice of a MutableCollection with a slice of a larger size")
因此您无法通过以下方式更改 MutableCollection 的长度
(默认)下标设置器,尝试这样做会中止程序。
作为一个例子,让我们定义一个符合以下条件的“最小”类型
MutableCollection:
struct MyCollection : MutableCollection, CustomStringConvertible {
var storage: [Int] = []
init(_ elements: [Int]) {
self.storage = elements
}
var description: String {
return storage.description
}
var startIndex : Int { return 0 }
var endIndex : Int { return storage.count }
func index(after i: Int) -> Int { return i + 1 }
subscript(position : Int) -> Int {
get {
return storage[position]
}
set(newElement) {
storage[position] = newElement
}
}
}
然后用相同长度的切片替换集合的一部分
作品:
var mc = MyCollection([0, 1, 2, 3, 4, 5])
mc[1 ... 2] = mc[3 ... 4]
print(mc) // [0, 3, 4, 3, 4, 5]
但对于不同的长度,它会因运行时异常而中止:
mc[1 ... 2] = mc[3 ... 3]
// fatal error: Cannot replace a slice of a MutableCollection with a slice of a smaller size
注意符合MutableCollection的具体类型可能
允许在其下标设置器中进行不同长度的替换,
就像Array 一样。