我是Swift(以及iOS编程)的新手,我正在努力寻找某些数据结构是否包含元素。 更具体地说,我创建了一个空集,我想在进一步计算后插入元素:
var moviesInItinerary : NSMutableSet? = nil
然后,我只想在集合为空或者它不包含给定元素时继续计算。 我写这样的条件是这样的:
if((moviesInItinerary?.count == 0) || (!moviesInItinerary!.containsObject(movies[currentMovie.row].title)))
但是,当我尝试运行此代码时,我收到此错误:
致命错误:在解包可选值时意外发现nil
执行这些检查的安全方法是什么?
答案 0 :(得分:4)
您应该阅读Swift的可选类型。盲目地进入而不理解它们肯定会导致编程错误。
var moviesInItinerary : NSMutableSet? = nil
我将其改为:
var moviesInItinerary : NSMutableSet = NSMutableSet()
然后,moviesInIineine 不能为。如果你真的希望它是一个可选类型(意味着它可能是零),那么将你的条件改为:
if let moviesSet = moviesInItineraray? {
// use moviesSet in here. It will not be nil.
}
答案 1 :(得分:1)
您可以这样做:
if !(moviesInItinerary?.containsObject(movies[currentMovie.row].title) == true) {
// When we get here, we know either moviesInItinerary is nil, or the NSMutableSet
// does not contain our movie.
}
这是有效的,因为可选链接使moviesinItinerary?.constainsObject(movies[currentMovie.row].title)
返回类型为Bool?
的值。如果nil
为moviesInItinerary
,因为true
为零,则它不会与moviesInItinerary
进行比较。如果nil
不是containsObject
,则true
将返回false
或true
,然后与count
进行比较。 }。也无需检查zero
是否为count
,因为这是多余的。 {{1}}为零的集合显然不包含您的对象。
答案 2 :(得分:1)
将moviesInItinerary
键入为NSMutableSet?
表示NSMutableSet
可以为零,并且您似乎永远不会为其分配对象。
这一行:
var moviesInItinerary : NSMutableSet? = nil
声明moviesInItinerary
本身 NSMutableSet
或nil
(在此特定情况下,因为除了{{ 1}},它就像那样)。
Swift鼓励人们使用不可变变量,并在有意义的时候避免使用可空变量。如果您始终需要nil
作为有效集,并且您不需要使用其他集覆盖它,则声明它的最佳方式是:
moviesInItinerary
从作业的右侧,Swift知道let moviesInItinerary = NSMutableSet()
的类型应该是moviesInItinerary
,因此无需明确键入它。它也知道它不能是NSMutableSet
,并且在初始化之后它不能指向不同的对象。
由于它不能nil
,您也不再需要使用nil
运算符:只需.?
即可。