Видеокурсы по изучению языка программирования Swift. Подробнее

Связанные значения

Если вы нашли опечатку в тексте, выделите ее и нажмите CTRL + ENTER.

Примеры в предыдущей секции показывают, как кейсы перечисления по праву считаются объявленными значениями. Вы можете установить Planet.earth как константу или переменную и посмотреть какое значение она содержит. Однако бывает удобно хранить связанные значения других типов вместе с этими значениями кейсов перечисления. Это позволяет вам хранить дополнительную пользовательскую информацию вместе со значением кейса и разрешает изменять эту информацию каждый раз как вы используете этот кейс перечисления в вашем коде.

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

Для примера, предположим систему инвентаризации, которая должна отслеживать товар двумя различными типа штрих-кодов. Одни товары имеют коды типа 1D формата UPC-A, которые используют цифры от 0 до 9. Каждый штрих-код имеет свою “систему цифр”, где идут пять цифр “кода производителя” и пять цифр “кода продукта”. Затем идет “проверочная” цифра, которая проверяет, что код был отсканирован корректно:

Другие продукты имеют маркировку штрих-кодом 2D формата QR, который может использовать любой символ из ISO 8859–1 и может закодировать строку длинною 2953 символа:

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

В Swift перечисления для определения штрих-кода продукта одного из двух типов может выглядеть следующим образом:

enum Barcode {
    case upc(Int, Int, Int, Int)
    case qrCode(String)
}

Читается это вот так:

“Объявление перечисления типа Barcode, которое берет два значения, одно из которых upc, со связанным значением типа (Int, Int, Int, Int) и значение qrCode со связанным значением типа String.”

Объявление не дает никакого значения типа Int или String, оно лишь определяет типы связанных значений, которые константы или переменные Barcode могут содержать, когда они равны Barcode.upc или Barcode.qrCode.

Новые штрих-коды могут быть созданы с помощью любого типа:

var productBarcode = Barcode.upc(8, 85909, 51226, 3)

В этом примере мы создаем новую переменную productBarcode и присваиваем ей значение Barcode.upc со связанным кортежем значений (8, 85909, 51226, 3).

Этому же продукту может быть присвоено другое значение кода:

productBarcode = .qrCode("ABCDEFGHIJKLMNOP")

Здесь исходный Barcode.upc и его целочисленные значения заменены новым Barcode.qrCode и его строковым значением. Константы и переменные типа Barcode могут хранить или .upc или .qrCode (вместе со связанными значениями), но они могут хранить только один из них в любое время.

Различные типы штрих-кодов могут быть проверены инструкцией switch как и раньше. В этот раз связанные значения могут быть извлечены как часть инструкции switch. Вы извлекаете каждое связанное значение как константу (с префиксом let) или как переменную (префикс var) для использования внутри тела оператора switch:

switch productBarcode {
case .upc(let numberSystem, let manufacturer, let product, let check):
    print("UPC: \(numberSystem), \(manufacturer), \(product), \(check).")
case .qrCode(let productCode):
    print("QR code: \(productCode).")
}
// Выводит "QR code: ABCDEFGHIJKLMNOP."

Если все связанные значения для членов перечисления извлекаются как константы или переменные, то для краткости вы можете разместить одиночное let или var перед именем члена:

switch productBarcode {
case let .upc(numberSystem, manufacturer, product, check):
    print("UPC : \(numberSystem), \(manufacturer), \(product), \(check).")
case let .qrCode(productCode):
    print("QR code: \(productCode).")
}
// Выводит "QR code: ABCDEFGHIJKLMNOP."

 

Swift: 
3.0