苹果似乎声称,Swift中的Optional
类型比Objective-C中的nil
更安全,但我不明白为什么。
实现上的主要区别是什么,使得Optional
比nil
更安全,这会如何影响我的代码?
苹果似乎声称,Swift中的Optional
类型比Objective-C中的nil
更安全,但我不明白为什么。
实现上的主要区别是什么,使得Optional
比nil
更安全,这会如何影响我的代码?
if let ...
和 guard
语法明确表示“只有这些变量有值时才执行此操作”。!
语法会使程序在变量为 nil
时崩溃,而程序员并未预期该变量为 nil
。nil
的方式可能会让程序继续执行,直到 nil
不再可接受为止。一个常见的例子是 nil
的 NSString
变量。许多 API 调用都可以接受 nil
的 NSString
,除了构造 NSAttributedString
(它不会接受 nil
的 NSString
参数并且会导致应用程序崩溃)。因此,当你意外地得到一个 NSString
变量变成了 nil
,你的应用程序可能会在一段时间后崩溃,因为它尝试使用该 nil
值构造属性字符串。一般来说,在编程中,我们希望避免没有值的变量(null
或nil
),因为使用它们通常会导致未定义的行为(异常、错误、崩溃)。
例如,常见做法是将Array
引用设置为空数组而不是nil
。在空数组上,我们可以使用所有的Array
方法,例如indexOf
或count
。在nil
上使用这些方法会导致崩溃。
可选项允许我们指定某些变量永远不为空,因此我们可以安全地使用它们,并且编译器检查nil
永远不会分配给它们。此外,编译器强制执行每个从可选类型转换为非可选类型的显式转换(我们始终在需要时检查nil
)。
因此,答案是可选项:
从而防止编程错误。
还要注意的是,尽可能避免使用可选项。可选项最强大的功能是大多数变量都不是可选项。
nil
。可选类型的威力在于将 nil
限制在特定的库中。 - Sulthannil
上的 [indexOfObject:
或 count
] 会导致崩溃。 - jscs[nil indexOfObject:x]
不会返回 NSNotFound
。这就是我试图说明的重点。有些情况下语言是幸运的,比如 string.length == 0
或 array.count == 0
,但有很多情况下应用程序不会崩溃,但会导致意外状态。在 SO 上最常见的 Obj-C 问题之一是:“我的方法没有被调用。”。 - Sulthan为了避免问题,我经常在使用变量之前检查它是否为nil
。然而,偶尔会出现值作为nil
的情况,让我感到惊讶——有时候是我自己忘记检查。
随着我在Swift中编写越来越多的代码,我发现使用可选变量确实提供了很多便利,避免忽略对nil
值的检查。我不太记得有任何由于nil
变量访问而导致的崩溃(除非我强制解包某个变量;因此,除非您知道自己在做什么,否则不要强制解包)。
此外,我曾经在许多地方编写过很多像这样的代码:
if (obj != nil) {
obj.property = ...
}
obj?.property = ...