func myFunction() -> NSData { ... }
上面的意思是myFunction
返回一个NSData
.
func myFunction() -> NSData? { ... }
上面的意思是myFunction
返回一个类型的值Optional<NSData>
(也称为NSData?
)。Optional
是一个enum
有两种情况:.some(value)
和.none
(也称为nil
)。因此,该函数返回一个NSData
(包装在.some
案例中)或nil
.
func myFunction() -> NSData! { ... }
上面的意思是myFunction
返回一个 type 的值Optional<NSData>
,就像NSData?
前面例子中的返回类型一样。
但是,使用的!
意思是,如果您以myFunction()
不进行类型检查的方式使用值,编译器将尝试为您解开返回的值。所以如果你这样说:
let maybeLength = myFunction()?.length
然后编译器将看到您将 的返回值myFunction
视为Optional<NSData>
. 但如果你这样说:
let dataLength = myFunction().length
然后编译器会看到Optional<NSData>
没有length
成员,所以它会假装你写了这个:
let dataLength = myFunction()!.length
如果编译成功,它将继续。
这种行为是在Swift Evolution 提案 SE-0054, Abolish ImplicitlyUnwrappedOptional
type中定义的。
现在让我们最终考虑一下:
func myFunction() -> NSData! { ... }
let data = myFunction()
data?.write()
是什么类型的data
?data
编译器必须根据 . 右侧的表达式来推断=
. 正如我在上面的示例中所解释的,类型myFunction()
是Optional<NSData>
. 所以类型data
是Optional<NSData>
,也叫NSData?
。
data
编译器在生成' 类型时不会遇到任何问题NSData?
,因此没有理由隐式解开 . 的返回值myFunction
。