Swift under the hood: Optionals
The question mark syntax isn’t all there is to an Optional
One special thing about Swift is the beauty of Optionals — where a variable can or can not have a value. If there’s no value, then it’s nil (a.k.a. null or empty). To declare a variable is an optional, you mark it with a question mark. But how does the compiler know that question mark means optional? We’ll go through what’s happening with this shorthand syntax.
First things first — Enums with associated values
I know, I KNOW, this article is supposed to be about what the heck an optional really is. But first, we need to understand Enumerations (a.k.a enums) and what does it mean that an Enum has an associated value.
Enumerations are used to provide a way to define a group of type-safe values, depicted as cases.
Associated values are stored values that a case may or may not define, and they kind of look like parameters.
To learn more, visit the Swift Docs for Enumerations — Associated Values
Revealing what an Optional really is
Now that’s settled, let’s explain what an Optional is.
An optional is an enum that has an associated value.
@frozen public enum Optional<Wrapped>: ExpressibleByNilLiteral {
/// The absence of a value.
///
/// In code, the absence of a value is typically written using the `nil`
/// literal rather than the explicit `.none` enumeration case.
case none
/// The presence of a value, stored as `Wrapped`.
case some(Wrapped)
}
The code above is copied and pasted straight from Swift Standard Library’s code. To open this up, you can define an optional variable in Xcode like the following:
var x: Int? = .none
When you right-click on .none, and select “Jump to Definition,” you’ll see the public information in all of it’s glory. (Also don’t forget the fact that Swift is also completely open-sourced)
To drive the point home, here’s how to declare a variable with both the shorthand syntax and using the enum:
var num1: Int? = nil
var num2: Optional<Int> = .none // Same implementation without the shorthand
var string1: String? = "Hello, World!"
string1 = .some("Hello, World!") // Same value as string1
As a quick note, if you try to initialize string2 as any other data type besides String, then you’ll get the compiler error Cannot convert value of type ‘Int’ to expected argument type ‘String’
For further reading, you can read about Optionals on Apple’s developer docs on their website here, or you can hit Cmd + Shift + 0 (zero) whenever you have Xcode open to browse through the docs.
Once you use optionals in your programming, they quickly become second nature. It’s great to pause to learn how they work under the hood, so you can appreciate optionals a little bit more. I know I do
Thanks for reading! For more Swift content, be sure to follow me on Medium.