Accessing an Enumeration association value in Swift Accessing an Enumeration association value in Swift swift swift

Accessing an Enumeration association value in Swift


For sake of completeness, enum's association value could be accesed also using if statement with pattern matching. Here is solution for original code:

enum Number {  case int (Int)  case float (Float)}let integer = Number.int(10)let float = Number.float(10.5)if case let .int(i) = integer {  print("integer is \(i)")}if case let .float(f) = float {  print("float is \(f)")}

This solution is described in detail in: https://appventure.me/2015/10/17/advanced-practical-enum-examples/


The value is associated to an instance of the enumeration. Therefore, to access it without a switch, you need to make a getter and make it available explicitly. Something like below:

enum Number {    case int(Int)    case float(Float)    func get() -> NSNumber {        switch self {        case .int(let num):            return num        case .float(let num):            return num        }    }}var vInteger = Number.int(10)var vFloat = Number.float(10.5)println(vInteger.get())println(vFloat.get())

Maybe in the future something like that may be automatically created or a shorter convenience could be added to the language.


It surprises me that Swift 2 (as of beta 2) does not address this. Here's an example of a workaround approach for now:

enum TestAssociatedValue {  case One(Int)  case Two(String)  case Three(AnyObject)  func associatedValue() -> Any {    switch self {    case .One(let value):      return value    case .Two(let value):      return value    case .Three(let value):      return value    }  }}let one = TestAssociatedValue.One(1)let oneValue = one.associatedValue() // 1let two = TestAssociatedValue.Two("two")let twoValue = two.associatedValue() // twoclass ThreeClass {  let someValue = "Hello world!"}let three = TestMixed.Three(ThreeClass())let threeValue = three. associatedValue() as! ThreeClassprint(threeValue.someValue)

If your enum mixes cases with and without associated values, you'll need to make the return type an optional. You could also return literals for some cases (that do not have associated values), mimicking raw-value typed enums. And you could even return the enum value itself for non-associated, non-raw-type cases. For example:

enum TestMixed {  case One(Int)  case Two(String)  case Three(AnyObject)  case Four  case Five  func value() -> Any? {    switch self {    case .One(let value):      return value    case .Two(let value):      return value    case .Three(let value):      return value    case .Four:      return 4    case .Five:      return TestMixed.Five    }  }}let one = TestMixed.One(1)let oneValue = one.value() // 1let two = TestMixed.Two("two")let twoValue = two.value() // twoclass ThreeClass {  let someValue = "Hello world!"}let three = TestMixed.Three(ThreeClass())let threeValue = three.value() as! ThreeClassprint(threeValue.someValue)let four = TestMixed.Fourlet fourValue = four.value() // 4let five = TestMixed.Fivelet fiveValue = five.value() as! TestMixedswitch fiveValue {case TestMixed.Five:  print("It is")default:  print("It's not")}// Prints "It is"