Pebellslearn by building
0%
RoadmapsMatrixCoursesSandboxSign in
Operators  ›  Capstone Project

The Nil-Coalescing Operator

Nil-Coalescing 12 minThe nil-coalescing operator unwraps an optional or falls back to a default of the same type, evaluating the default only when needed.

The Nil-Coalescing Operator

Sprout's habit card shows the reminder time, or "No reminder" when there is none. With if let and else that takes five lines. The nil-coalescing operator does it in one, and it is one of the most used operators in real Swift.

The rule

a ?? b: use a if it is there, otherwise b.

a is an optional. If it holds a value, the result is that value, unwrapped. If it is nil, the result is b, the default.

let reminder: String? = nil
let shown = reminder ?? "No reminder"    // "No reminder"

let typed = "15"
let minutes = Int(typed) ?? 0             // 15
let bad = Int("fifteen") ?? 0             // 0

Three facts make it predictable:

  • The result is not optional. shown is a plain String, ready to use.
  • The default must match the wrapped type. With a String? on the left, the default must be a String. reminder ?? 0 does not compile.
  • The default is only worked out when needed. If a has a value, b is never evaluated, so an expensive default costs nothing most of the time.

You can chain defaults. Swift tries each one left to right and takes the first that is not nil:

let title = customName ?? suggestedName ?? "New habit"

It is a short form of this:

let shown: String
if let reminder { shown = reminder } else { shown = "No reminder" }

Use ?? when there is a sensible default. When nil needs different behaviour, not just a different value, if let or guard let is clearer.

The shortcut

Read ?? as "or else". Look at the left side: value present? Take it. nil? Move one step right and ask again. The last item in a chain should be non-optional, so the answer is always a plain value.

Naming a new Sprout habitStep 1 of 4
  1. The line

    let title = customName ?? suggestedName ?? "New habit" with customName nil and suggestedName "Drink water".

Drills

Answer fast — trust the rule.

quick drill

With let note: String? = "Stretch first", what is note ?? "None"?

quick drill

What is Int("abc") ?? -1?

quick drill

With let r: String? = nil, why does r ?? 0 fail to compile?

quick drill

With a and b both String? values set to nil, what is a ?? b ?? "c"?

Remember

  • a ?? b: use a if it is there, otherwise b.
  • Read ?? as "or else"; the result is never optional when the last item is not.
  • The default must match the wrapped type, and is only evaluated when needed.

Practice — level up

0/1 solved

Write your answer, then compare it with a rubric and a model answer.

Explain?? or if let?

Sprout parses a typed goal with Int(text). Explain what Int(text) ?? 1 does for the inputs "4" and "four", and describe one situation where if let would be a better choice than ??.