Search code examples
iosswiftoption-typeforced-unwrapping

Not using unwrapping in guard statements


I understand the use of optionals enough to know when its necessary to unwrap an optional using the exclamation point. Why is it that the exclamation point isn't needed in a guard statement?

This code works and compiles but doesn't use exclamation points:

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)")
}

This code also works if you do put the exclamation points:

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)")
}

Isn't this a little contradictory or can someone clearly explain why the exclamation point isn't needed?


Solution

  • guard let unwrapped = optional is an Optional Binding (no link available directly to the correct book section, unfortunately). It safely tries to unwrap the value in the optional. If there is a value, the unwrap succeeds, and the value is assigned to the given name.

    You should heavily favor the use of optional bindings, with either guard or if (the difference is the scope of the "unwrapped" name) over the use of forced unwrapping with !. A failed force unwrap is a fatal error; your program will simply crash.