Swift - 检测项是否已插入NSMutableSet

时间:2017-08-24 10:18:04

标签: swift set

这更多是为了兴趣而不是问题,但我有一个NSMutableSet,从UserDefaults检索,我的目标是将一个项目附加到它然后再写回来。我使用的是NSMutableSet,因为我只想要插入唯一的项目。

要插入的对象类型是自定义类,我已覆盖hashCodeisEqual

var stopSet: NSMutableSet = []

if let ud = UserDefaults.standard.object(forKey: "favStops") as? Data {
  stopSet = NSKeyedUnarchiver.unarchiveObject(with: ud) as! NSMutableSet
}

stopSet.add(self.theStop!)

let outData = NSKeyedArchiver.archivedData(withRootObject: stopSet)
UserDefaults.standard.set(outData, forKey: "favStops")
NSLog("Saved to UserDefaults")

我得到集合,调用mySet.add(obj)然后将集合写回UserDefaults。一切似乎工作得很好(据我所知),似乎没有重复。

但是,可以判断对mySet.add(obj)的调用是否实际上导致项目被写入集合。 mySet.add(obj)没有返回值,如果你使用Playgrounds(而不是一个项目),你会在右侧的输出中得到一个关于该组是否实际根据方法调用而改变的指示。

我知道集合并不意味着存储重复的对象所以理论上我应该相信这一点,但我只是想知道集合是否确实返回了一个你可以访问的响应 - 而不是只是在插入之前获取长度和之后,如果我真的想知道!

1 个答案:

答案 0 :(得分:1)

Swift有自己的原生类型Set,因此您应该使用它而不是NSMutableSet

Set insert方法实际返回Bool,表示插入是否成功,您可以在函数签名中看到: mutating func insert(_ newMember: Element) -> (inserted: Bool, memberAfterInsert: Element)

以下测试代码展示了此行为:

var set = Set<Int>()
let (inserted, element) = set.insert(0)
let (again, newElement) = set.insert(0)

print(inserted,element) //true, 0
print(again,oldElement) //false,0

如果插入成功,则元组的第二个值返回新插入的元素,否则返回oldElement。 oldElement在每个方面都不一定与您尝试插入的元素相同。 (因为对于自定义类型,您可以以不比较该类型的每个属性的方式定义isEqual方法。)

您不需要处理insert函数的返回值,如果您只是像这样编写insert,则没有编译器警告:

set.insert(1)