Swift Optionals: как их использовать (с примерами)

В этой статье вы узнаете о необязательном, его вариантах использования и необязательной обработке в Swift.

В предыдущей статье мы узнали о различных типах данных, доступных в Swift, а также заметили, что переменная или константа, объявленная для этих типов, содержит значение по умолчанию.

Пример:

 пусть someValue = Int () print (someValue) 

Когда вы запустите программу, вывод будет:

 0

Однако в Swift есть еще один тип данных, называемый Optional, значение по умолчанию которого равно null ( nil). Вы можете использовать optional, если хотите, чтобы переменная или константа не содержали в себе значения. Необязательный тип может содержать значение или отсутствовать (нулевое значение).

Технически, вы можете думать как обувная коробка как необязательный предмет. Обувная коробка может содержать или не содержать обувь. Таким образом, вы должны знать заранее, когда достаете обувь из коробки.

Как объявить необязательным?

Вы можете просто представить тип данных как необязательный, добавив !или ?к Type. Если необязательный параметр содержит значение, он возвращает значение как Optional, в противном случае - nil.

Пример 1. Как объявить необязательный параметр в Swift?

 var someValue:Int? var someAnotherValue:Int! print(someValue) print(someAnotherValue) 

Когда вы запустите программу, вывод будет:

 ноль ноль

В приведенной выше программе мы инициализировали необязательный тип с помощью ?и !. Оба способа допустимы для создания необязательного, но есть одно важное различие, которое мы рассмотрим ниже.

Объявление необязательного Int означает, что переменная либо будет иметь целочисленное значение, либо не иметь значения. Поскольку переменной не присвоено никакого значения, вы можете видеть оба printвывода оператора nilна экране.

Пример 2: Назначение значения и доступ к нему из необязательного

 let someValue:Int? = 5 print(someValue) print(someValue!) 

Когда вы запустите программу, вывод будет:

 Необязательно (5) 5 

В приведенной выше программе мы объявили необязательный Intтип и присвоили ему значение 5.

Как видите, печать необязательного as print(someValue)не дает вам, 5но Optional(5). Это имеет вид , как описано выше: Optional. Чтобы получить из него доступ , нам нужен механизм, называемый разворачиванием .

Вы можете развернуть необязательный элемент, добавив !символ в конце переменной / константы, как в следующей строке print(someValue!). print(someValue!)разворачивает необязательное и выводит 5на экран.

Однако помните, что этот вид механизма развертывания следует использовать только в том случае, если вы уверены, что дополнительный параметр обязательно будет иметь значение при доступе к нему.

Пример 3: явное объявление развернутой необязательной

Вы также можете создать развернутый необязательный элемент как:

 let someValue:Int! = 5 print(someValue) 

Когда вы запустите программу, вывод будет:

 5

В приведенной выше программе Int!создается развернутый необязательный элемент, который автоматически разворачивает значение, пока вы к нему обращаетесь, так что вам не нужно каждый раз добавлять !символ.

Будьте уверены, что при использовании таких опций переменная всегда должна иметь значение при доступе к ней. Если вы этого не сделаете, вы получите фатальную ошибку.

Пример 4: Неустранимая ошибка при доступе к необязательному развёрнутому нулю

 var someValue:Int! var unwrappedValue:Int = someValue //crashes due to this line 

Когда вы запустите программу, вы получите сбой как фатальную ошибку: при развертывании необязательного значения неожиданно обнаружен nil, потому что код unwrappedValue:Int = someValueпытается присвоить значение из Optional someValue переменной unwrappedValue.

Однако somevalue - это Optionalтип, содержащий nilзначение. Попытка присвоить значение nil переменной unwrappedValue, которая не является необязательной, приведет к сбою.

Существуют различные методы работы с этим случаем, которые описаны ниже.

Дополнительная обработка

Чтобы использовать значение необязательного параметра, его необходимо развернуть. Лучший способ использовать необязательное значение - условное развертывание, а не принудительное развертывание с использованием !оператора.

Это потому, что при условном разворачивании спрашивается Проверить, имеет ли эта переменная значение? . Если да, укажите значение, иначе будет обработан случай nil.

Напротив, принудительное развертывание говорит о том, что эта переменная имеет значение, пока вы ее используете . Следовательно, при принудительном развертывании переменной, имеющей значение nil, ваша программа выдаст неожиданно обнаруженный nil при развертывании необязательного исключения и аварийно завершится . Некоторые методы условного разворачивания объясняются ниже:

1. Если-заявление

You can use if statement and compare optional with nil to find out whether a optional contains a value or not. You can use the comparison operator "equal to" operator (==) or the "not equal to" operator (!=) in the if statement.

Example 5: Optional handling with if else statement

 var someValue:Int? var someAnotherValue:Int! = 0 if someValue != nil ( print("It has some value (someValue!)") ) else ( print("doesn't contain value") ) if someAnotherValue != nil ( print("It has some value (someAnotherValue!)") ) else ( print("doesn't contain value") ) 

When you run the program, the output will be:

 doesn't contain value It has some value 0 

In the above program, the code inside if statement executes if an optional contain a value, otherwise the statement inside the else block executes. The major drawback of optional handling using this technique is, you still need to unwrap the value from optional using ! operator.

2. Optional Binding (if-let)

Optional binding helps you to find out whether an optional contains a value or not. If an optional contains a value, that value is available as a temporary constant or variable. Therefore, optional binding can be used with if statement to check for a value inside an optional, and to extract that value into a constant or variable in a single action.

Example 5: Optional handling using if let statement

 var someValue:Int? var someAnotherValue:Int! = 0 if let temp = someValue ( print("It has some value (temp)") ) else ( print("doesn't contain value") ) if let temp = someAnotherValue ( print("It has some value (temp)") ) else ( print("doesn't contain value") ) 

When you run the program, the output will be:

 doesn't contain value It has some value 0 

In the above program, the code inside if statement executes if the optional contains a value. Otherwise the else block gets executed. The if-let statement also automatically unwraps the value and places the unwrapped value in temp constant. This technique has major advantage because you don't need to forcely unwrap the value although being certain an optional contains a value.

3. Guard statement

You can use guard to handle optionals in Swift. Don't worry if you don't know what guard is. For now, just think of guard as an if-else condition with no if block. If the condition fails, else statement is executed. If not, next statement is executed. See Swift guard for more details.

Example 6: Optional handling using guard-let

 func testFunction() ( let someValue:Int? = 5 guard let temp = someValue else ( return ) print("It has some value (temp)") ) testFunction() 

When you run the program, the output will be:

 It has some value 5

In the above program, the guard contains a condition whether an optional someValue contains a value or not. If it contains a value then guard-let statement automatically unwraps the value and places the unwrapped value in temp constant. Otherwise, else block gets executed and and it would return to the calling function. Since, the optional contains a value, print function is called.

4. Nil-coalescing operator

In Swift, you can also use nil-coalescing operator to check whether a optional contains a value or not. It is defined as (a ?? b). It unwraps an optional a and returns it if it contains a value, or returns a default value b if a is nil.

Example 7: Optional handling using nil-coalescing operator

 var someValue:Int! let defaultValue = 5 let unwrappedValue:Int = someValue ?? defaultValue print(unwrappedValue) 

When you run the program, the output will be:

 5

В приведенной выше программе переменная someValue определена необязательно и содержит значение nil. Оператор объединения nil не может развернуть необязательный элемент, поэтому возвращает defaultValue. Таким образом, оператор print(unwrappedValue)выводит в консоли 5.

 var someValue:Int? = 10 let defaultValue = 5 let unwrappedValue:Int = someValue ?? defaultValue print(unwrappedValue) 

Когда вы запустите программу, вывод будет:

 10

Однако в приведенной выше программе необязательная переменная someValue инициализируется значением 10. Таким образом, оператор объединения nil успешно разворачивает значение из someValue. Следовательно, оператор someValue ?? defaultValueвозвращает 10, а оператор print(unwrappedValue)выводит 10 в консоли.

Интересные статьи...