当前位置: 首页 > 面试题库 >

Xcode 8中隐式展开的可选分配

汪皓
2023-03-14
问题内容

在Xcode 8发行版中,我发现了一个奇怪的场景。

这是代码,

let implicitlyUnwrappedOptionalString: String! = "implicitlyUnwrappedOptionalString"
let foo = implicitlyUnwrappedOptionalString

print(implicitlyUnwrappedOptionalString)
print(foo)

结果如下:

implicitlyUnwrappedOptionalString
Optional("implicitlyUnwrappedOptionalString")

上面的这些表明,当我为没有显式类型的变量分配一个 隐式解包的optional时 ,该类型将被推断为一个可选类型,而不是它最初的类型,也就是
隐式解开的optional

我的Xcode已更新至8。任何人都可以验证Xcode 7.x中的行为吗?

更改是由于Swift版本更改还是Xcode?


问题答案:

这是SE-0054废除ImplicitlyUnwrappedOptional类型的结果,该类型已在Swift
3中实现。从该提案中摘录(添加了重点):

但是,外观!在属性或变量声明的类型的末尾不再指示该声明具有IUO类型;相反,它指示(1)声明具有可选类型,并且(2)声明具有指示其值可以隐式强制的属性。…

如果可以使用强可选类型对表达式进行显式类型检查,则它将是。
但是,如果需要,类型检查器将转为强制使用可选。此行为的结果是,引用指向声明为T!的值的任何表达式的结果。将是T型还是T?型。例如,在以下代码中:

let x: Int! = 5
let y = x
let z = x + 0

…x被声明为IUO,但是由于y类型的初始化程序正确检查为可选变量,因此y将绑定为Int?类型。但是,z的初始值设定项不会将x声明为可选项(没有+的重载是可选项)的类型检查,因此编译器会强制执行可选项,并将初始值设定项检查为Int。

在您的情况下,作业

let foo = implicitlyUnwrappedOptionalString

foolet y = x 建议中的示例所示,使之具有较强的可选性。

可以foo通过添加显式类型注释 创建IUO

let foo: String! = implicitlyUnwrappedOptionalString

但通常,您应该尝试摆脱代码中的IUO,如同一建议中所述:

除了一些特定的情况外,可选选项始终是更安全的选择,我们希望鼓励人们使用它们而不是IUO。



 类似资料:
  • 问题内容: 为什么无法对隐式解包的可选变量进行突变? 这是一个重现问题的简短示例: 带整数 问题答案: 更新: Xcode Beta 5中的一个小警告已解决此问题: 该数组可以按预期工作,但是现在看来整数仍然需要显式拆包以允许使用 当前,这仅仅是Optionals的本质(无论是否隐式解包)。unwrap运算符返回一个不变的值。这可能是固定的,或者将来会提供更好的解决方案。 目前唯一的解决方法是将数

  • 在Swift 4.0中,以下代码不可编译: 现在我想象是

  • 我正在学习Swift,我对隐式展开选项有疑问。 我有一个返回字符串可选的函数: 以及执行安全展开的if语句,它使用隐式展开可选作为其常量: 在第一行中,apt按照应有的方式展开(结果窗格显示“404”),但在其他两行中,apt没有展开:结果窗格和控制台都显示打印的值是可选的(“404”)和找到的公寓:可选(“404”),为了让404出现在控制台上,我必须使用!符号,如果我理解正确,它只需要手动展开

  • 如果像Apple在Swift编程中所说的隐式展开选项应该总是有一个值,那么为什么不使用非选项来代替呢?我知道非选项不能赋值为nil,但还有其他区别吗?

  • 所以我问了这个问题,看起来原因是 之所以不起作用,是因为操作符采用了inout参数,而隐式取消包装的选项不是。然而,在 操作符与隐式unwrapped选项一起工作,这意味着二进制操作符不需要inout参数。所以我的问题是,为什么一元运算符和二元运算符有不同的参数要求?对我来说,能够使用Int似乎有点傻

  • 在编写一个新的swift类时,当(不)使用隐式展开选项而不仅仅是普通选项时,我仍然不是100%舒服。据我所知,如果你从来没有期望它的值为零,那么把它指定为隐式未包装(可选)应该是可以的。如果为nil,则为异常事件,应导致运行时错误。 例如,这个简单的登录视图包含两个text field成员变量: 在上面的类中,emailField和passField都被归类为隐式展开选项,因为我从来没有期望它们在