SWIFT / CHAPTER 11

Protocols and throwing operations

Advanced

Specify capabilities and handle recoverable failures explicitly.

By the end of this chapter

  • Implement a protocol requirement
  • Declare a throwing function
  • Match a specific error case

The idea

A protocol defines requirements that conforming types provide. It can describe behavior without choosing whether implementations use structs or classes. Clients depend on the capability rather than the concrete representation. Ensure every conformer preserves the intended meaning, such as units and failure behavior, so substituting one implementation for another remains sensible.

Swift makes throwing calls explicit with try. A throwing function can report a typed error value, and do/catch provides a handling boundary. Define an Error-conforming enum when callers need to distinguish cases. try? converts a thrown error into absence, which is useful only when discarding the error detail matches the requirement; do not erase information the caller needs.

Swift example
enum CountError: Error { case negative }
func checked(_ value: Int) throws -> Int {
    guard value >= 0 else { throw CountError.negative }
    return value
}
do {
    print(try checked(-1))
} catch CountError.negative {
    print("Count must be nonnegative")
} catch {
    print("Other failure")
}
Result
Count must be nonnegative

The guard throws before a value is returned. The matching catch handles the specific error without executing the successful print.

Try it yourself

Create a protocol for producing a label and two conforming value types, then call both through the shared capability.

Use your own editor for this exercise. Runnable challenges on CodeQuest are available for JavaScript, Python, and SQL.

CHECK YOUR UNDERSTANDING

Chapter checkpoint

What does try? checked(-1) evaluate to using checked above?