不在守卫声明中使用展开

时间:2016-07-15 19:37:16

标签: ios swift optional forced-unwrapping

我理解使用选项足以知道何时需要使用感叹号展开可选项。为什么在警卫声明中不需要感叹号?

此代码可以工作和编译,但不使用感叹号:

struct Blog{

  var author:String?
  var name: String?

}

func blogInfo2(blog:Blog?){
  guard let blog = blog else {
    print("Blog is nil")
    return
  }
  guard let author = blog.author, name = blog.name else {
    print("Author or name is nil")
    return
  }
  print("BLOG:")
  print(" Author: \(author)")
  print(" name: \(name)")
}

如果您确实放了感叹号,此代码也可以使用:

struct Blog{

  var author:String?
  var name: String?

}

func blogInfo2(blog:Blog?){
  guard let blog = blog! else {
    print("Blog is nil")
    return
  }
  guard let author = blog.author!, name = blog.name! else {
    print("Author or name is nil")
    return
  }
  print("BLOG:")
  print(" Author: \(author)")
  print(" name: \(name)")
}

这不是一个有点矛盾,或者有人可以清楚地解释为什么不需要感叹号吗?

3 个答案:

答案 0 :(得分:4)

guard let unwrapped = optionalOptional Binding(不幸的是,没有直接提供给正确的图书部分的链接)。 安全地尝试解包可选中的值。如果有值,则解包成功,并将值分配给给定名称。

你应该非常赞成使用可选绑定,使用guardif(不同之处在于#34; unwrapped"名称的范围),而不是使用强制解包与!。失败的强制解包是致命错误;你的程序会崩溃。

答案 1 :(得分:2)

  

我理解使用选项足以知道何时需要使用感叹号展开可选项。

如果你做出那个断言,我觉得你没有足够了解Swift Optionals。

“可选项”背后的合同是它可能是也可能不是;你不知道它,因此你必须打开它(比如打开一个盒子,看看里面的内容),然后再说出来。

该框可能为空(nil可选),也可能包含值。

使用强制展开(<{1}})的原因很少非常少,在大多数(但不是全部)案例中,它通常被视为不良做法。

要继续比喻,通过强行展开内容,你会说这个框中有东西,我希望你相信我,不要检查

知道一个空盒子会崩溃您的应用程序,这是一件非常危险的事情,考虑在Swift中引入Optionals来保护你免受这些崩溃首先。

!语句基本上是在框内窥视,如果有什么东西,他们会把它给你,但是如果框是空的,它们也会让你有机会做其他事情。

Xcode在使用IBOutlets时强制展开,因为按设计合同是这些对象将在您可以使用时在您的视图控制器中,但除非您100%确定某个值不是if let/guard let,否则使用nil语句几乎总是更好(并且将来证明) (或guard)。

根据我的经验,即使您确定,仍然更安全地抛出if并忘记可能出现的未来问题。

答案 2 :(得分:1)

感叹&#34;力量&#34;打开一个可选的。 guard letif let在不强制执行任何操作的情况下展开它,因此不会使用感叹号。