在Swift中有可能吗?如果没有,那么是否有解决方法?
protocol MyProtocol { func doSomething() } extension MyProtocol { func doSomething() { /* return a default value or just leave empty */ } } struct MyStruct: MyProtocol { /* no compile error */ }
优点
不涉及Objective-C运行时 (至少没有明确 涉及 )。这意味着您可以NSObject使其符合结构,枚举和非类。同样,这意味着您可以利用强大的泛型系统。
NSObject
*当遇到符合此类协议的类型时, *您始终可以确保满足所有要求 。它始终是具体实现或默认实现。这就是“接口”或“合同”在其他语言中的行为方式。
缺点
对于非Void要求,您需要具有一个合理的默认值,但这并非总是可能的。但是,当您遇到此问题时,这意味着该要求实际上应该没有默认实现,或者您在API设计期间犯了一个错误。
Void
您无法区分默认实现和根本没有实现 ,至少没有用特殊的返回值解决该问题。考虑以下示例:
protocol SomeParserDelegate { func validate(value: Any) -> Bool
}
如果您提供仅返回的默认实现true-乍一看就可以了。现在,考虑以下伪代码:
true
final class SomeParser { func parse(data: Data) -> [Any] { if /* delegate.validate(value:) is not implemented */ { /* parse very fast without validating */ } else { /* parse and validate every value */ } } }
无法实现这种优化-您不知道委托是否实现了一种方法。
尽管有多种方法可以解决此问题(使用可选的闭包,针对不同的操作使用不同的委托对象,仅举几例),但该示例清楚地提出了问题。
@objc optional
@objc protocol MyProtocol { @objc optional func doSomething() } class MyClass: NSObject, MyProtocol { /* no compile error */ }
它 要求所有符合类型都必须与Objective-C兼容 ,从而严重限制了协议的功能 。这意味着,仅继承自NSObject该类的类可以遵循此类协议。没有结构,没有枚举,没有关联的类型。
您必须始终 通过可选调用或检查符合类型 是否实现了可选方法来检查是否实现了可选方法 。如果您经常调用可选方法,这可能会引入很多样板。