2

この(かなり退屈な)コードを考えてみましょう:

class SCell : NSObject {}
class SHeader : NSObject {}

class Cell : SCell {}
class Header : SHeader {}
struct Model {}

protocol PA {
    typealias Ce = SCell
    typealias He = SHeader
    func doThis(cell : PA.Ce,header : PA.He)
}

extension PA {
     func doThis(cell : PA.Ce,header : PA.He) {
        print("A's implementation")
    }
}

protocol PB:PA {

}

extension PB {
    func doThis(cell : PA.Ce,header : PA.He) {
        print("B's implementation")
    }
}

class A  : PA {
    func doSomethingElse() {
        self.doThis(cell: Cell(), header: Header())
    }
}

class B : A,PB {

}

class C : B {}

let c = C()
c.doSomethingElse()

驚いたことに、これは印刷を開始しました

「Aの実装」

デフォルトの実装のdoThis(cell:header)一部としてオーバーライドされるため、「Bの実装」を出力することを期待していました。PBこれは驚くべきことに起こりませんでした。

さらに興味深いのは、これを行うと次のようになることです。

class B: A,PB {
    override func doSomethingElse() {
        self.doThis(cell: Cell(), header: Header())
    }
}

プリントアウト始めました

Bの実装

なぜこうなった?

4

1 に答える 1

1

プロトコル拡張はポリモーフィズムを行わないため、この場合、必要がなければ動的にディスパッチされません。その理由は、プロトコルはクラス、構造体、および列挙型で採用できるためです。

別の理由は、PAでプロトコルのデフォルトの実装を提供しているため、メソッドが欠落している場合にのみPBが有効になるためです (これは、 PAで既に定義されているためではありません)。

詳細については、こちらをご覧ください。

于 2016-11-22T12:01:53.137 に答える