Enums
An Enum (short for Enumeration) defines a common type for a group of related values. They allow you to work with these values in a type-safe way, preventing errors from "magic strings" or numbers.
Basic Syntax
You can define possible options using the case keyword. Cases can be on separate lines or on a single line separated by commas. Both are identical in functionality.
// Separate lines
enum CompassDirection {
case north
case south
case east
case west
}
// Single line (more compact)
enum CompassDirection {
case north, south, east, west
}Once defined, you can use "dot syntax" as a shortcut to change the value:
var direction = CompassDirection.north
direction = .south // Type is inferred as CompassDirectionAssociated Values
Enums can store additional information that varies for each case.
enum Barcode {
case upc(Int, Int, Int, Int)
case qrCode(String)
}
let productCode = Barcode.upc(8, 85909, 51226, 3)Raw Values
Raw values are prepopulated default values that back each case. Unlike associated values, raw values must be of the same type for all cases, and each value must be unique.
Supported Types
Raw values can be Strings, Characters, or any Integer or Floating-point number type.
Implicit vs Explicit
- Integers: If you don't provide a value for the first case, it starts at
0. If you set the first case to1, subsequent cases will auto-increment (2, 3, 4...). - Strings: If you don't provide a value, the case name itself becomes the raw value.
enum Planet: Int {
case mercury = 1, venus, earth, mars // earth is 3
}
enum State: String {
case active, inactive // rawValue of .active is "active"
}Enums with Methods
Enums are more than just a list of names; they can have methods and computed properties to encapsulate behavior.
enum MessageStatus {
case sent, delivered, read, failed
// Computed property for UI logic
var iconName: String {
switch self {
case .sent: "paperplane"
case .delivered: "checkmark"
case .read: "checkmark.seal"
case .failed: "exclamationmark.circle"
}
}
func canRetry() -> Bool {
self == .failed
}
}
let status = MessageStatus.failed
print(status.iconName) // "exclamationmark.circle"
if status.canRetry() { /* Show retry button */ }