Optionals

In Swift, you can use optionals to represent variables and constants that could be nil or a value.

Any data type in Swift can be made optional by adding a question mark after the data type name.

For instance, let’s create an optional String:

var name: String?

The value of this string is now nil.

To use an optional value, you need to unwrap it from the optional.

In other words, you can use an if statement to make sure the value is not nil. Otherwise, your program will crash.

In this guide, you learn how to work with optionals in Swift. You will also learn how to unwrap optionals in multiple different ways. More importantly, you learn how and when you are going to use optionals in Swift.

This chapter is part of a completely free Swift for Beginners guide. Make sure you have completed all the chapters from the start before reading this one.

Disclaimer: To learn Swift, you have to repeat everything you see in this guide and in the following guides. If you only read the guides, you are not going to learn anything!

Optionals in Swift

In Swift, an optional represents a variable or constant is either a value or nil.

Optionals are used when you want to create a variable but do not know its initial value yet. With optionals, you do not need to specify the initial value. Instead, it becomes nil.

In Swift, optionals are among the most confusing topics among beginner programmers.

Optionals are characterized by question marks and exclamation marks.

Before jumping into optionals, let’s briefly discuss what is nil as we are going to talk about it a lot in this guide.

Nil in Swift: The Empty Value

In Swift, you can represent empty values with a special object called nil.

The formal definition of nil is the “intentional absence of a value”.

The nil keyword is reserved for representing variables and constants that are intentionally left without values.

But why is there such a special value for representing blank values?

This is because a computer does not understand emptiness as we do.

If you do not give a variable an initial value, Swift has no idea what to do. However, if you specify a variable to be nil, you are letting Swift know this variable is empty.

Now, let’s jump into the main topic, that is, optionals in Swift.

What Problems do Optionals Solve?

So far in this series, you have assigned values to constants and variables countless times.

For instance:

var name = "Alice"
let num: Int = 30
var n: Double = 7.23

In the above, you specify the variable or constant and give it a value right on the line.

But sometimes you may want to declare a variable without assigning a value to it. This is because you might not know its value yet.

As a matter of fact, this is really common in Swift.

However, you cannot just leave the assignment part out to create these empty variables.

For example, this piece of code fails miserably:

var name
let num: Int
var n: Double

Output:

error: type annotation missing in pattern

It is good that this causes an error because Swift wants to ensure each variable/constant holds a value.

But how do you create empty variables then?

To declare an empty variable, you need to use optionals.

In the next section, you learn how.

How to Create an Optional?

By definition, an optional can store a value or it can be nil.

In other words, optionals let you create variables without assigning a value to them.

Any data type can be made optional in Swift.

To create an optional, add a question mark after the data type.

var name: DataType?

This creates an optional variable of type DataType and calls it a name. The variable now has an initial value of nil.

For instance, let’s create a variable called name that is an optional String:

var name: String?

This creates an optional String called name and initializes it to nil.

Let’s display the value to see that it is indeed the case:

print(name)

Output:

nil

Swift treats optional values as something that could be nil or a value.

This has to be taken into account when working with these optional values. This is because you cannot use optionals as-is in your code.

Let’s continue with the optional name example by assigning a string to the variable:

name = "Alice"

Now the name is no longer nil.

Let’s print the name again:

print(name)

Output:

Optional("Alice")

The result is Optional(“Alice”) because the data type of name is still an optional String, not just a String.

In other words, the name is still wrapped inside an optional even though it is not nil anymore.

To use the value as a String, you need to unwrap the optional string.

In the next section, you are going to learn how to do this.

How to Use Optional Values in Swift?

As stated earlier, you cannot use optional values as-is.

This is because before using the possible value stored inside an optional, you need to make sure it is not nil.

In other words, you need to unwrap the optional.

To unwrap an optional in Swift, you have 5 options:

  1. Force-unwrapping
  2. If-Else statement
  3. Optional binding
  4. Optional chaining
  5. Nil coalescing

Let’s take a look at each of these approaches in more detail.

I know, it is going to be a lot of information. However, all of this belongs to the basics of Swift. Thus you really need to learn it.

Force-Unwrapping

The easiest way to unwrap an optional is by force-unwrapping.

Notice that this operation is dangerous as it might crash your program!

To force-unwrap an optional, use an exclamation mark after the optional name.

optional!

This unwraps the optional value whether it is nil or not. If the value is nil, the program crashes. If the optional was not nil, force-unwrapping returns the value stored inside the optional.

For example, let’s create an optional Int called age, and unwrap it:

var age: Int? = 10

var ageUnwrapped = age!

print(ageUnwrapped)

Output:

10

Force-unwrapping an optional is a controversial way to unwrap an optional!

This is because when you force-unwrap, you are essentially saying “I do not care if the optional is nil or not, just give me the value.”

In other words, if you force-unwrap an optional that is nil, your program is going to crash.

For instance, this piece of code is going to stall your program:

var age: Int?
print(age!)

This happens because you try to print the force-unwrapped age which is nil.

As a rule of thumb, do not force-unwrap an optional unless you are 100% sure it is not nil!

Now, let’s take a look at a more safe approach to unwrapping optionals.

If-Else Statement

A safer way to unwrap an optional is by using an if statement to check whether it is nil or not.

This way you can be 100% sure of whether the optional is nil or not before unwrapping and using the value.

For example, let’s check if an optional string is nil before printing it:

var name: String?

if name != nil {
    print(name!)
} else {
    print("Name is nil")
}

Output:

Name is nil

In this piece of code:

  • We first check if a name is nil.
  • If the name is not nil, we can safely force-unwrap it.
  • If the name is nil, we do not try to force-unwrap the value. Instead, we display a message.

In this case, the optional name turned out to be nil.

Thus, the else block was executed and the nil was never used because it would have crashed the program.

This is a common and safe way to unwrap optionals in Swift.

Next, let’s take a look at optional binding.

Optional Binding

Another common way to unwrap an optional value is by using what is called optional binding.

Optional binding means you bind the value of an optional to a variable/constant for later use. If the optional is nil, this binding does not happen.

Optional binding is characterized by the if-let statement that is somewhat similar to an if-statement:

if let valueName = optional {
    // actions
}

If the optional is not nil, its value is assigned to a constant called valueName. You can then use the valueName in the if-block to perform actions on it.

Notice that you cannot access the unwrapped optional outside of this if-block.

Once again, this is best demonstrated via an example.

For instance, let’s assign an optional string to a constant called wordUnwrapped and print it out:

var word: String? = "Hello world!"

if let wordUnwrapped = word {
    print("The word is", wordUnwrapped)
}

Output:

The word is Hello world!

Notice that if you wanted to assign the unwrapped optional to a variable, you should use if-var instead:

var word: String? = "Hello world!"

if var wordUnwrapped = word {
    print("The word is", wordUnwrapped)

}

Next, let’s talk about optional chaining and how to unwrap chains of optional values.

Optional Chaining

Sometimes in Swift, you have an optional object that has optional properties.

When you have chains of optionals, you have to make sure none of those are nil.

To do this, you need to use what is called optional chaining.

Optional chaining happens by adding a question mark before the dot notation. This tells Swift to first ensure the value is not nil before accessing its properties.

Here is what optional chaining looks like in general:

something?.someValue?.someMethod()

Where something and someValue are both optional objects that could be nil.

For example, you could have an optional Boss object that has an optional Employee object with a name.

To access the name you cannot use the dot notation as you have used to:

boss.employee.name

This is because if the boss or the employee happens to be nil, the program crashes!

Instead, you have to rely on optional chaining:

boss?.employee?.name

This line checks that the boss is not nil before it tries to access the employee. Then it makes sure the employee is not nil before accessing its name.

Here is the full example:

struct Employee {
    var name: String?
}

struct Boss {
    var name: String
    var employee: Employee?
}

var emp1: Employee? = Employee(name: "Bob")
var boss1: Boss? = Boss(name: "Alice", employee: emp1)

// Optional chaining
if let name = boss1?.employee?.name {
    print(name)
}

Output:

Bob

With optional chaining, you can safely read an attribute of a chain of optional values.

Last but not least, let’s talk about nil coalescing as a way to unwrap optionals in Swift.

Nil coalescing

In Swift, you can unwrap optionals with a nil coalescing operator.

This way you can provide a default value that is going to be used if the unwrapped optional is nil.

The nil coalescing is characterized by the double question mark operator.

Here is the syntax:

optional ?? defaultValue

Where:

  1. optional is optional that could be nil or a value.
  2. defaultValue is the default value that is going to be used if the optional turns out to be nil.

For example, let’s print an optional string called name such that if it is nil, we use a default value “Default”.

var name: String?

print(name ?? "Default")

Output:

Default

Next Chapter: Arrays in Swift

Conclusion

Today you learned what are optionals in Swift.

To recap, it is quite common for you to have a variable but do not know its value in advance.

However, you cannot initialize “empty” variables because Swift has no idea what a variable without a value means.

In this case, you need to use optionals.

An optional is something that can be nil or a value.

You can make any basic data type optional by adding a question mark after specifying the data type of a variable/constant.

var name: String?

When dealing with optionals, you always need to make sure they are not nil before using the possible values in them.

In other words, you need to unwrap optional values before using them.

Here is a short recap of all the optional unwrapping methods:

// #1 Force-Unwrapping
optional!

// #2 If-Else
if optional != nil {
    // force-unwrap the value
}

// #3 Optional Binding
if let value = optional {
    // actions with 'value'
}

// #4 Optional Chaining
someObject?.someValue?.someMethod()

// #5 Nil-Coalescing
optional ?? defaultValue

In the next two chapters, you are going to learn really useful and important built-in data types in Swift called Array and Dictionary.

Next Chapter: Arrays in Swift