2016-04-02 7 views
1

similar questionsがありますが、これは最新のSwift 2.2バージョンです。うまくいけば、これは私の心の中でProtocol-Oriented Programmingの大きな障害のように思えるので、今は解決策があります。以下型配列をプロトコルにキャストするときの致命的なエラー:Objective-Cからブリッジできません

はエラーでlet resultsに割り当てることに失敗:Execution was interrupted, reason: EXC_BAD_INSTRUCTION (code=EXC_I386_INVOP, subcode=0X0).

protocol P: class { 
    var value:Int {get} 
} 

class X: P { 
    var value = 0 

    init(_ value:Int) { 
     self.value = value 
    } 
} 

func getItems() -> [P] { 
    let items: [X] = [X(1), X(2), X(3)] 
    return items 
} 

let results: [P] = getItems() 

は、それがに準拠したプロトコルの配列としてのクラスの配列を治療する方法はありますか?これは、言語のための本当にシンプルで自然な要求のように特に重くprotocol-orientedです。

@objcまたはflatMapは、依存関係のチェーンとパフォーマンスに大きな影響を与えるため、使用したくありません。これはハックです。私はこれをネイティブに動作させたい、あるいはApple/Swiftのオープンソースチームに提出してくれるバグです。

答えて

0

は、私はあなたの質問を理解していないかもしれませんが、[P]は動作しませんので、[X]をキャストし、なぜこれが

protocol P: class { 
    var value:Int {get} 
} 

class X: P { 
    var value = 0 

    init(_ value:Int) { 
     self.value = value 
    } 
} 

func getItems() -> [P] { 
    let items: [P] = [X(1), X(2), X(3)] 
    return items 
} 

let results = getItems() 
results.forEach { (p) in 
    print(p.value) 
} 
/* 
1 
2 
3 
*/ 

動作しますか?次の例を参照してください!

あなたは結果

let arrX = results.flatMap { $0 as? P } 
let arrX1 = results.flatMap { $0 as? P1 } 
print(arrX, arrX1) // [X, X, X] [X1, X1] 
からXとX1タイプのアイテムを分離したい場合はflatMapを使用すると、良いアイデアである理由、ある
protocol P: class { 
    var value:Int {get} 
} 
protocol P1: class { 
    var value: Double { get } 
} 
protocol Z {} 
class X: P,Z { 
    var value = 0 

    init(_ value:Int) { 
     self.value = value 
    } 
} 
class X1: P1,Z { 
    var value = 0.0 

    init(_ value:Double) { 
     self.value = value 
    } 
} 

func getItems() -> [Z] { 
    // the only common type of all items is protocol Z !!!! 
    let items: [Z] = [X(1), X(2), X(3), X1(1), X1(2)] 
    return items 
} 

let results = getItems() 
print(results.dynamicType) 
results.forEach { (p) in 
    if let p = p as? P { 
     print("P:", p.value) 
    } 
    if let p = p as? P1 { 
     print("P1:", p.value) 
    } 
} 
/* 
Array<Z> 
P: 1 
P: 2 
P: 3 
P1: 1.0 
P1: 2.0 
*/ 

関連する問題