我注意到Swift中的一个常见模式是
var x:[String:[Thing]] = [:]
所以,当您要"将项目添加到其中一个数组"时,您不仅可以
x[which].append(t)
您必须
if x.index(forKey: which) == nil {
x[which] = []
}
x[which]!.append(s!)
真的,是否有一种更快的方式来说
x[index?!?!].append??(s?!)
- 虽然这是关于样式的问题,但由于Swift的复制性质, ,性能似乎是一个关键问题。
(请注意,显然您可以为此使用扩展名;这是关于迅速的问题。)
swift 4更新:
从Swift 4开始,字典具有subscript(_:default:)
方法,因此
dict[key, default: []].append(newElement)
附加到已经存在的数组或空数组。示例:
var dict: [String: [Int]] = [:]
print(dict["foo"]) // nil
dict["foo", default: []].append(1)
print(dict["foo"]) // Optional([1])
dict["foo", default: []].append(2)
print(dict["foo"]) // Optional([1, 2])
在 swift 4.1 (当前在beta中)这也是 fast,在这里比较哈米什的评论。
swift< = 3:的先前答案,据我所知,没有办法"创建或更新"字典用单个下标调用值。
除了您写的内容外,您还可以使用nil-coalescing操作员
dict[key] = (dict[key] ?? []) + [elem]
或可选链接(如果附加操作,则返回nil
可以执行不是):
if dict[key]?.append(elem) == nil {
dict[key] = [elem]
}
如SE-0154中提到的制作数组的副本。
通过实施SE-0154,您将能够突变词典值而不制作副本:
if let i = dict.index(forKey: key) {
dict.values[i].append(elem)
} else {
dict[key] = [key]
}
目前,最有效的解决方案由Rob Napier给出在swift中的字典中,随着值的性能非常慢?如何正确优化或正确构造?:
var array = dict.removeValue(forKey: key) ?? []
array.append(elem)
dict[key] = array
一个简单的基准确认" Rob的方法"是最快的:
let numKeys = 1000
let numElements = 1000
do {
var dict: [Int: [Int]] = [:]
let start = Date()
for key in 1...numKeys {
for elem in 1...numElements {
if dict.index(forKey: key) == nil {
dict[key] = []
}
dict[key]!.append(elem)
}
}
let end = Date()
print("Your method:", end.timeIntervalSince(start))
}
do {
var dict: [Int: [Int]] = [:]
let start = Date()
for key in 1...numKeys {
for elem in 1...numElements {
dict[key] = (dict[key] ?? []) + [elem]
}
}
let end = Date()
print("Nil coalescing:", end.timeIntervalSince(start))
}
do {
var dict: [Int: [Int]] = [:]
let start = Date()
for key in 1...numKeys {
for elem in 1...numElements {
if dict[key]?.append(elem) == nil {
dict[key] = [elem]
}
}
}
let end = Date()
print("Optional chaining", end.timeIntervalSince(start))
}
do {
var dict: [Int: [Int]] = [:]
let start = Date()
for key in 1...numKeys {
for elem in 1...numElements {
var array = dict.removeValue(forKey: key) ?? []
array.append(elem)
dict[key] = array
}
}
let end = Date()
print("Remove and add:", end.timeIntervalSince(start))
}
结果(在1.2 GHz Intel Core M5 MacBook上)适用于1000键/1000个元素:
您的方法:0.470084965229034零合并:0.460215032100677可选的链接0.397282958030701删除并添加:0.160293996334076
和1000键/10,000个元素:
您的方法:14.6810429692268零合并:15.1537700295448可选的链接14.4717089533806删除并添加:1.54668599367142