当我在下面的问题中解释逻辑错误时:
我偶然发现了一个我无法解释的特殊情况。
如上面的主题所示,我们可以在b
和if let b = rhs ...
子句中明确说明范围 - 本地不可变的类型,比如guard let b = rhs ... else
,它们是相同的可选类型作为rhs
的{{1}}值(尝试分配)到b
,在这种情况下,“可选绑定”将始终成功:
let a: Int?
// ...
if let b: Int? = a { // will always succeed, 'Int?' to 'Int?'
print(b.dynamicType) // Optional<Int>
}
我们可以讨论是否应该允许这样做,因为这本质上是一个膨胀的块本地分配,但这不是这个问题的重点。相反,解释以下特点:
如果我们明确声明上面的b
属于隐式解包的可选类型(此处为:Int!
),那么b
范围内的if let
由于某种原因,子句只是一个常规的非解包可选项,即Int
。
let a: Int? = nil
if let b: Int! = a {
print(b.dynamicType) // Optional<Int>
/* why not ImplicitlyUnwrappedOptional<Int> ? */
}
问题:
b
是一个隐式解包的可选(Int!
) - 转换为“常规”可选(Int?
)(在if let
子句中)?我只是注意到上述“影子转换”自然不适用于对隐式展开的期权的期权的常规分配
let c: Int? = 10
let d: Int! = c
print(f.dynamicType) // ImplicitlyUnwrappedOptional<Int>
如果我们使用从非可选(if let
)到隐式展开的可选(Int
)
Int!
块本地赋值,则不会出现
let c = 10
if let d: Int! = c {
print(d.dynamicType) // ImplicitlyUnwrappedOptional<Int>
}
在以下评论中来自@Sulthan的反馈后,我们发现如果上面的a
是双重可选(Int??
),则不会出现此“影子转化”,例如
let a: Int?? = 10
if let b: Int! = a {
print(b.dynamicType) // ImplicitlyUnwrappedOptional<Int>
}
if let b: Int? = a {
print(b.dynamicType) // Optional<Int>
}
我使用的是Swift 2.2 / Xcode 7.3。