2017-09-18 4 views
0

I Container benötigen Sie nochEquatable Artikel für in NICHT Generic Klasse (zum Beispiel UI-Klassen Anfang von Storyboard). Ich brauche wie dieseAllgemeine Klasse gleichzusetzen auf Swift

var items: [Equatable]? 

aber es funktioniert nicht, Equatable brauchen Generisches. das Problem, dass es keine gemeinsame Equatable Klasse gibt.


Ok - Zum Generischen! Aber wenn ich das tue

class Item<Value: Equatable>: Equatable { 
    var value: Value 
    init(_ value: Value) { 
     self.value = value 
    } 
    //Equatable 
    public static func ==(lhs: Item, rhs: Item) -> Bool { 
     return (lhs.value == rhs.value) 
    } 
} 

dann werde ich gezwungen werden, den Typ in meiner nonGeneric-UI-Klasse anzugeben. Gefällt Ihnen dieses

var items: [Item<WhatShouldBeHere?>]? 

aber wieder kommen wir zu dem Problem, dass es keine existieren üblich ist Equatable Klasse


Alle Lösungen für Container für alle gleichzusetzen?

+0

Verwandte: [Betrieb auf einem Array von Strukturen Implementierung zu] (https: //stackoverflow.com/questions/41298464/operation-on-an-array-of-structs-implementing-equatable) – Hamish

Antwort

3

Anstelle von existenziellen Typen, benötigen Sie eine Art Radiergummi verwenden:

public struct AnyEquatable: Equatable { 
    public let value: Any 
    private let equals: (Any) -> Bool 

    public init<E: Equatable>(_ value: E) { 
     self.value = value 
     self.equals = { ($0 as? E) == value } 
    } 

    public static func == (lhs: AnyEquatable, rhs: AnyEquatable) -> Bool { 
     return lhs.equals(rhs.value) || rhs.equals(lhs.value) 
    } 
} 

Beispiel Nutzung:

let items = [ 
    AnyEquatable(1), 
    AnyEquatable(1.23), 
    AnyEquatable(true), 
    AnyEquatable("some string") 
] 

let desired = "some string" 
let desiredAsAnyEquatable = AnyEquatable(desired) 
let desiredDescription = String(reflecting: desired) 

for item in items { 
    let itemDescription = String(reflecting: item.value) 
    let isEqualToDesired = item == desiredAsAnyEquatable 
    print("\(itemDescription) is \(isEqualToDesired ? "": "not ")equal to \(desiredDescription)") 
} 

Beispiel Ausgabe:

1 nicht gleich "zu einige Zeichenfolge "

1.23 ist nicht gleich" einige stri ng“

wahr ist nicht gleich "some string"

"some string" ist gleich "some string"

+0

großartige Idee create equals Methode in generischen init !!! Danke, –

+0

Beachten Sie, dass Sie 'Equals (_ :)' für beide 'Lhs' und' RHs' aufrufen sollten, um die Symmetrie beim Vergleich einer Unterklasse mit einer Superklasseninstanz beizubehalten. – Hamish

+0

@Hamish Gut, das hatte ich nicht bedacht. also 'lhs.equals (rhs.value) || rhs.equals (lhs.value) '? – Alexander

Verwandte Themen