Labs ICT
โญ Pro Login

Enumerations

Defining custom value types with cases.

Enumerations in Swift

Enumerations (enums) define a group of related values and let you work with those values in a type-safe way. Unlike enums in many other languages, Swift enums are full-fledged types โ€” they can have methods, computed properties, and conform to protocols.

enum Direction {
    case north
    case south
    case east
    case west
}

let heading = Direction.north
print(heading) // north
Try it Yourself ->

Raw Values

Enums can have raw values โ€” pre-populated values of a specific type like String, Int, or Double. Raw values are useful when you need to initialize an enum from a value or convert an enum back to its raw representation.

enum Planet: Int {
    case mercury = 1
    case venus = 2
    case earth = 3
    case mars = 4
}

let earthNumber = Planet.earth.rawValue
print(earthNumber) // 3

// Initialize from raw value
if let planet = Planet(rawValue: 2) {
    print(planet) // venus
}

enum ASCIIControlCharacter: Character {
    case tab = "\t"
    case lineFeed = "\n"
    case carriageReturn = "\r"
}
Try it Yourself ->

Associated Values

This is where Swift enums really shine. Associated values let you attach additional data to each case. Each case can have different associated values of different types, making enums incredibly flexible.

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

let productBarcode = Barcode.upc(8, 85909, 51226, 3)
let anotherBarcode = Barcode.qrCode("ABCDEFGH")

switch productBarcode {
case .upc(let manufacturer, let product, let check, let _):
    print("UPC: \(manufacturer)-\(product)-\(check)")
case .qrCode(let code):
    print("QR: \(code)")
}
// UPC: 8-85909-51226-3
Try it Yourself ->

Switching on Enums

The switch statement is the natural way to work with enums. Swift ensures that your switch is exhaustive โ€” you must handle every possible case. This prevents you from forgetting to handle a new case when you add one later.

enum TrafficLight {
    case red, yellow, green
}

let light = TrafficLight.green

switch light {
case .red:
    print("Stop")
case .yellow:
    print("Caution")
case .green:
    print("Go")
}
// Go
Try it Yourself ->

Enum Methods

Enums can have methods and computed properties just like structs and classes. This lets you encapsulate behavior related to the enum's cases right inside the enum itself.

enum ServerResponse {
    case result(String, String)
    case failure(String)
    
    func message() -> String {
        switch self {
        case .result(let success, let message):
            return "\(success): \(message)"
        case .failure(let error):
            return "Failure: \(error)"
        }
    }
}

let response = ServerResponse.result("200", "OK")
print(response.message()) // 200: OK
Try it Yourself ->

CaseIterable Protocol

By conforming to CaseIterable, your enum automatically gets an allCases property that contains all of its cases. This is incredibly useful for iterating over all possible values without maintaining a separate array.

enum Season: CaseIterable {
    case spring, summer, autumn, winter
}

for season in Season.allCases {
    print(season)
}
// spring
// summer
// autumn
// winter

print("There are \(Season.allCases.count) seasons")
// There are 4 seasons
Try it Yourself ->

๐Ÿงช Quick Quiz

What makes enums powerful in Swift?