2017-01-07 8 views
1

私は困惑しています...コンパイラが何を考えているのか分かりませんが、私はこれを90%確信しています可能でなければなりません:タイプ 'Generic <String>'の値を 'Generic <Any>'に変換できません

class Generic<Type: Any> { 

} 

protocol Foo { 
    func bar(_ baz: Generic<Any>) 
} 

class SomeFoo: Foo { 
    func bar(_ baz: Generic<Any>) { 
     print("Got", baz) 
    } 
} 

let someFoo = SomeFoo() 
let generic = Generic<String>() 

someFoo.bar(generic) // Compile error: Cannot convert value of type 'Generic<String>' to expected argument type 'Generic<Any>' 

ここでは何が起こっていますか?回避策はありますか?確かにいくつかの回避策が必要です...

+2

'Generic 'は 'Generic 'に変換できるのはなぜですか? '(String) - > Void'は'(Any) - > Void'に変換できません。ユーザー定義のジェネリック型は共分散をサポートしていません。 https://en.wikipedia.org/wiki/Covariance_and_contravariance_(computer_science) – jtbandes

+0

しかし、 'String is Any' ...関数が' Any'をとり、 'String'を与えた場合、それは文句なしです –

+1

' String'は 'Any'ですが、'(String) - > Void'は ''(Any) - > Void'ではありません。私の指摘は、これは*常に*働くことはできないということです。一部の言語では、動作する必要があることを指定できます。 Swiftの現在のバージョンはその1つではありません。 – jtbandes

答えて

1

これは、Swiftのユーザータイプ(これは私が知っている限り)ではサポートされていません。 BTWのObjective-Cジェネリックは、何らかの形で共分散をサポートします。私は2つのオプションからあなたの状況では
を選択したい:

  1. がfoo関数によって受け入れられる非汎用プロトコルを作成し、Genericクラスで、このプロトコルを実装する一般的なメイクバー機能
関連する問題