2014-10-15 4 views
39

Ist es möglich, in Swift eine Tupelaufzählung zu erstellen?Enum von Tupeln in Swift

Ich möchte etwas bauen, wie:

enum ErrorCode: (Int, String) { 
    case Generic_Error = (0, "Unknown") 
    case DB_Error = (909, "Database") 
} 

Aber es lässt sich nicht kompilieren ... Gibt es eine Möglichkeit, ein ähnliches Ergebnis zu erzielen?

+2

Jemand weiß, warum dies in Swift nicht erlaubt ist? – agy

+0

können Sie Ihren Enum-Initialisierer für die Enumeration bereitstellen, die das Tupel erhalten und den Fall initialisieren würde, den Sie benötigen. Vielleicht ist das was du brauchst .. Und dann kannst du einfach MyCustomEnum (tuple: (1, "myString")) aufrufen und es würde funktionieren. Und innerhalb des Enum-Initialisierers kannst du Swifts verwenden, die im Schaltergehäuse passen, um das Wunder zu tun, das du brauchst. – Fawkes

Antwort

33

Es hängt davon ab, was Sie mit "ähnlich" meinen. Was ich tue, ist eine Struktur mit statischen konstanten Eigenschaften verwenden:

struct Trouble { 
    static let Generic_Error = (0, "Unknown") 
    static let DB_Error = (909, "Database") 
} 

Jetzt Dinge wie Trouble.Generic_Error im gesamten Code verwendbar sind.

14

können Sie so etwas tun, vielleicht:

enum ErrorCode { 
    case Generic_Error 
    case DB_Error 

    func values() -> (code: Int!, description: String?)! { 
     switch self { 
     case .Generic_Error: 
      return (0, "Unknown") 
     case .DB_Error: 
      return (909, "Database") 
     } 
    } 
} 

und Sie können später so etwas tun:

let errorCode: ErrorCode = ErrorCode.Generic_Error; 
if (errorCode.values().code == 0) { 
    // do the business here... 
} 
42

Swift Aufzählungen nicht Tupeln als Ausgangswert Typ haben kann.

Alternative Ansätze umfassen den Code zu speichern und eine Beschreibung von dem ableiten:

enum ErrorCode: Int, CustomStringConvertible { 
    case Generic = 0 
    case DB = 909 

    var description: String { 
     switch self { 
     case .Generic: 
      return "Unknown" 
     case .DB: 
      return "Database" 
     } 
    } 
} 

... oder Speichern von zugehörigen Werte für Code und Beschreibung in der Aufzählung Fällen selbst:

enum Error { 
    case Generic(Int, String) 
    case DB(Int, String) 
} 

Wenn Sie Wenn wir nur nach konstanten Werten suchen, würde der Vorschlag von @ matt, sie in einem struct zu organisieren, ebenfalls funktionieren.

+0

Printable wird umbenannt in CustomStringConvertible – Forke

+0

Wie würde 'Error' oben genau verwendet werden? – capikaw

+0

Oh yeah, Sie können Methoden (und schreibgeschützte vars) auf die Enum selbst setzen. So cool ... danke! –

-3
+0

Der Link zeigt ein Beispiel für eine Lösung, aber es ist bei weitem nicht so einfach wie "Enumeration als Int erstellen". Es entspricht im Wesentlichen dem ersten Codebeispiel von @ Mattt, basiert jedoch auf NSHTTPURLResponse.localizedStringForStatusCode für die Beschreibung anstelle eines Switch-over-Self. Sie sollten Ihre Antwort mit diesen Details bearbeiten. – Marmoy

6

Lösung ähnlich wie @holex, aber anstelle einer Funktion können Sie eine var verwenden.

enum SomeType { 
    case type1 
    case type2 
    case type3 

    var typeNameAndDescription: (name: String, description: String) { 
     switch self { 
     case .type1: 
      return ("type1 name", "type1 description") 
     case .type2: 
      return ("type2 name", "type2 description") 
     case .type3: 
      return ("type3 name", "type3 description") 
     } 
    } 
} 

und später:

let myType = SomeType.type1 
let typeName = myType.typeNameAndDescription.name 
let typeDescription = myType.typeNameAndDescription.description 
5

können Sie auf RawRepresentable entsprechen und (Int, String) als Self.RawValue zugehörigen Typ verwenden.

enum ErrorCode: RawRepresentable { 
    case Generic_Error 
    case DB_Error 

    var rawValue: (Int, String) { 
     switch self { 
     case .Generic_Error: return (0, "Unknown") 
     case .DB_Error: return (909, "Database") 
     } 
    } 

    init?(rawValue: (Int, String)) { 
     switch rawValue { 
     case (0, "Unknown"): self = .Generic_Error 
     case (909, "Database"): self = .DB_Error 
     default: return nil 
     } 
    } 
}