2016-12-05 1 views
1

je le code suivant:Swift ne peut pas trouver une surcharge lorsque les médicaments génériques impliqués

protocol MyEnum { 

} 

class MyClass { 
    func append(_ value: UInt8) { 
     print("uint8 \(value)") 
    } 

    func append(_ value: UInt16) { 
     print("uint16 \(value)") 
    } 

    func append<T: MyEnum>(_ value: T) { 
     print("myenum \(value)") 
    } 
} 

let c = MyClass() 

func appendAny<T>(_ value: T) { 
    switch value { 
    case let u8 as UInt8: 
     c.append(u8) 
    case let u16 as UInt16: 
     c.append(u16) 
    case let myenum as MyEnum: 
     c.append(myenum) 
    default: 
     assert(false) 
    } 
} 

L'erreur est signalée par le compilateur pour la ligne c.append(myenum) indiquant

ne peut invoquer « append » avec une liste d'arguments de type (MyEnum)

S'il vous plaît, expliquez-moi pourquoi cela se produit et quelle est la bonne solution dans ce cas. Je veux préserver mes surcharges, car quand il est appelé avec une instance concrète MyEnum, tout fonctionne bien.

+2

Ceci est une autre variante de http://stackoverflow.com/questions/33112559/protocol-doesnt-conform-to-itself: Un protocole n'est pas conforme à lui-même. Changez la troisième variante en 'func append (_valeur: MyEnum)' pour la faire compiler. –

+0

Merci @MartinR qui a fonctionné. Je suppose que j'ai surgégé cette méthode générique '' 'append''' un peu. –

Répondre

1

Comme Martin a noté dans son commentaire, vous devez changer votre dernière append() surcharge à:

func append(_ value: MyEnum) { 
    print("myenum \(value)") 
} 

Parce que vous voulez traiter la valeur comme « une instance d'un protocole », pas un « exemple d'un type concret qui arrive à se conformer au protocole ". Une instance qui a un protocole de type n'est pas aussi un type concret conforme à ce protocole.

Une autre note: puisque vous n'êtes pas vraiment en utilisant des contraintes génériques ou des propriétés de compilation du type T (seule coulée d'exécution), pourquoi ne pas simplement changer appendAny être:

func appendAny(_ value: Any) { 
    switch value { 
    case let u8 as UInt8: 
     c.append(u8) 
    case let u16 as UInt16: 
     c.append(u16) 
    case let myenum as MyEnum: 
     c.append(myenum) 
    default: 
     assert(false) 
    } 
}