Protocol содержит сигнатуры функций и свойств, которые должны быть реализованы соответствующими объектами, структурами, enum
В отличии от классов (у которых методы всегда вызываются у child объектов), протоколы могут вызвать методы и у parent, если не полагаться на type inference (аннотация типов let tmp: String
).
protocol MyProtocol {
func method1()
func method3()
}
extension MyProtocol {
func method1() {
print("method1 in protocol")
}
}
extension MyProtocol {
func method2() {
print("method2 in protocol")
}
}
class MyClass: MyProtocol {
func method1() {
print("method1 in class")
}
func method2() {
print("method2 in class")
}
func method3() {
print("method3 in class")
}
}
let instOfProtocol: MyProtocol = MyClass()
// witness table method dispatch
instOfProtocol.method1() // method1 in class
// direct (static) method dispatch
instOfProtocol.method2() // method2 in protocol
instOfProtocol.method3() // method3 in class
print("--- ---")
let instOfClass: MyClass = MyClass()
// virtual table method dispatch
instOfClass.method1() // method1 in class
instOfClass.method2() // method2 in class
instOfClass.method3() // method3 in class
У extension протоколов static method dispatch работает таким образом, что уже во время сборки компилятор знает, что вызывать и когда (те. в данном случае отдает приоритет типу для вызова выполнения адреса инструкций).
У протоколов witness table method dispatch производит вызов функции из таблицы, которая хранит сначала реализацию класса, потом уже протокола.
У классов virtual table method dispatch отдается приоритет всегда child объекту.
protocol Test {
optional func myFunc() {}
}
Обратите внимание, однако, что для того, чтобы это работало, ваш протокол должен быть помечен атрибутом @objc:
@objc protocol Test {
@objc optional func myFunc() {}
}
Это также означает, что этот протокол будет применим только к классам, но не к structs, enums and non-NSObject classes.
Это альтернатива extension
к протоколу.
-
Ретроактивное моделирование в POP - если вы определяете расширение для добавления новых функций к существующему типу, новые функции будут доступны для всех существующих экземпляров этого типа, даже если они были созданы до определения расширения.
-
Расширения могут добавлять новые вычисляемые свойства, но не могут добавлять сохраненные свойства или добавлять наблюдателей свойств к существующим свойствам.
5.4 Protocol Theme Folder | Back To iOSWiki Contents | 5.4.2 Associated Types Theme