3 回答

TA貢獻(xiàn)1966條經(jīng)驗(yàn) 獲得超4個(gè)贊
Swift的目標(biāo)之一是靜態(tài)調(diào)度,或者更確切地說是動(dòng)態(tài)調(diào)度的減少。然而,Obj-C是一種非常動(dòng)態(tài)的語言。您所看到的情況來自于兩種語言之間的聯(lián)系以及它們協(xié)同工作的方式。它不應(yīng)該真正編譯。
關(guān)于擴(kuò)展的一個(gè)要點(diǎn)是它們用于擴(kuò)展,而不是用于替換/覆蓋。從名稱和文檔中可以清楚地看出這是意圖。實(shí)際上,如果從代碼中取出Obj-C的鏈接(NSObject
作為超類刪除),它將無法編譯。
因此,編譯器正在嘗試確定它可以靜態(tài)調(diào)度的內(nèi)容以及動(dòng)態(tài)分派的內(nèi)容,并且由于代碼中的Obj-C鏈接,它正在陷入差距。dynamic
“工作” 的原因是因?yàn)樗仁筄bj-C連接所有東西,所以它總是動(dòng)態(tài)的。
因此,使用擴(kuò)展進(jìn)行分組并沒有錯(cuò),這很好,但是在擴(kuò)展中覆蓋它是錯(cuò)誤的。任何覆蓋都應(yīng)該在主類本身中,并調(diào)用擴(kuò)展點(diǎn)。

TA貢獻(xiàn)1776條經(jīng)驗(yàn) 獲得超12個(gè)贊
有一種方法可以實(shí)現(xiàn)類簽名和實(shí)現(xiàn)(在擴(kuò)展中)的清晰分離,同時(shí)保持在子類中具有覆蓋的能力。訣竅是使用變量代替函數(shù)
如果確保在單獨(dú)的swift源文件中定義每個(gè)子類,則可以使用計(jì)算變量進(jìn)行覆蓋,同時(shí)保持相應(yīng)的實(shí)現(xiàn)在擴(kuò)展中干凈地組織。這將繞過Swift的“規(guī)則”,并使您的課程的API /簽名整齊地組織在一個(gè)地方:
// ---------- BaseClass.swift ------------- public class BaseClass { public var method1:(Int) -> String { return doMethod1 } public init() {} } // the extension could also be in a separate file extension BaseClass { private func doMethod1(param:Int) -> String { return "BaseClass \(param)" } }
...
// ---------- ClassA.swift ---------- public class A:BaseClass { override public var method1:(Int) -> String { return doMethod1 } } // this extension can be in a separate file but not in the same // file as the BaseClass extension that defines its doMethod1 implementation extension A { private func doMethod1(param:Int) -> String { return "A \(param) added to \(super.method1(param))" } }
...
// ---------- ClassB.swift ---------- public class B:A { override public var method1:(Int) -> String { return doMethod1 } } extension B { private func doMethod1(param:Int) -> String { return "B \(param) added to \(super.method1(param))" } }
每個(gè)類的擴(kuò)展都能夠?yàn)閷?shí)現(xiàn)使用相同的方法名稱,因?yàn)樗鼈兪撬接械牟⑶冶舜瞬豢梢姡ㄖ灰鼈冊(cè)趩为?dú)的文件中)。
正如您所看到的,繼承(使用變量名稱)可以使用super.variablename正常工作
BaseClass().method1(123) --> "BaseClass 123" A().method1(123) --> "A 123 added to BaseClass 123" B().method1(123) --> "B 123 added to A 123 added to BaseClass 123" (B() as A).method1(123) --> "B 123 added to A 123 added to BaseClass 123" (B() as BaseClass).method1(123) --> "B 123 added to A 123 added to BaseClass 123"
- 3 回答
- 0 關(guān)注
- 756 瀏覽
添加回答
舉報(bào)