资讯专栏INFORMATION COLUMN

如何在Swift的Protocol中定义可选方法(译)

kidsamong / 2510人阅读

摘要:劣势对于有返回值的函数,你需要返回一个合适的默认值,这并不总是可行的。至少没有一个特殊的返回值来解决该问题。看一下下面的代码如果你提供了一个返回值为的默认实现,乍一看这么做没有问题。如果您经常调用可选方法,这可能会引入很多冗余代码。

使用默认实现(推荐)

protocol MyProtocol {
    func doSomething()
}

extension MyProtocol {
    func doSomething() {
        /* return a default value or just leave empty */
    }
}

struct MyStruct: MyProtocol {
    /* no compile error */
}

优势

没有牵扯到OC的runtime(至少没有明显的用到)。这就意味着你的structs、enum、或者非继承自NSObject的class去遵守它。此外,你还可以使用功能强大的泛型(generics) 。对泛型不了解的,可以通过这篇文章来了解泛型的基本使用。

当遇到符合此类protocol的类型时,你可以确保满足所有要求。它始终是具体实现或默认实现,这就相当于其他语言的“interfaces”或“contracts”的作用。

劣势

对于有返回值的函数,你需要返回一个合适的默认值,这并不总是可行的。但是,当你遇到了这个问题,就说明这个函数不应该声明为可选的,或者你在设计API的时候犯错了。

你无法区分是提供了一个默认的实现,还是并没有实现。至少没有一个特殊的返回值来解决该问题。看一下下面的代码:

protocol SomeParserDelegate {
    func validate(value: Any) -> Bool
}

如果你提供了一个返回值为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 */
        }
    }
}

这时是无法实现优化这个分支(if)的,因为你无法知道你的delegate是否实现了这个方法。 虽然有很多方法可以解决这个问题(使用optional closures,不同的delegate对象用于不同的操作等等),这个例子只是清晰地说明这么做存在的问题。

使用@objc optional

@objc protocol MyProtocol {
    @objc optional func doSomething()
}

class MyClass: NSObject, MyProtocol {
    /* no compile error */
}

优势

不需要默认实现,通过@objc optional 关键字修饰就可以了。

劣势

这样只能是符合OC中遵守protocol的类型,才能遵守该protocol,这样严重限制了Protocol的功能。这就意味着只有继承自NSObject的类才能遵守该协议。struct、enum都不行,也不能使用associated type。

你必须始终通过可选地调用或检查符合类型是否实现它来检查是否实现了可选方法。如果您经常调用可选方法,这可能会引入很多冗余代码。

原文链接

How to define optional methods in Swift protocol");

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/6728.html

相关文章

  • 如何SwiftProtocol定义可选方法

    摘要:劣势对于有返回值的函数,你需要返回一个合适的默认值,这并不总是可行的。至少没有一个特殊的返回值来解决该问题。看一下下面的代码如果你提供了一个返回值为的默认实现,乍一看这么做没有问题。如果您经常调用可选方法,这可能会引入很多冗余代码。使用默认实现(推荐) protocol MyProtocol { func doSomething() } extension MyProtocol {...

    番茄西红柿 评论0 收藏0
  • Swift 7 个陷阱以及如何避免

    摘要:原文链接前言伴随着语言的快速发展,我们对于苹果设备编程的认识也发生着变化。这其中的一些陷阱在官方的书里面,但是还有一些书中并没有提及。例如苹果提供了实现的用户体验,系统工具等功能很多框架。 作者: David Ungar,时间:2016/1/27 翻译:BigNerdCoding, 如有错误欢迎指出。原文链接 前言 伴随着Swift语言的快速发展,我们对于苹果设备编程的认识也发生着变...

    sourcenode 评论0 收藏0
  • iOS进阶

    摘要:然而,副作用对于系统的可测试性来说就是一剂毒药,并且可能会因应用程序和请求的不同而出现差异性。这些事件并不具备特定时序性,甚至它们可能同时发生。粘性动画中,粘性小球会根据移动距离的大小拥有不同的弹性程度。 PPAsyncDrawingKit - 实现了一系列基础 UI 控件的轻量级 ASDK 一款轻量级的 ASDK,实现了一系列基础 UI 控件。 iOS 开发之 Runtime 常用示...

    Cheng_Gang 评论0 收藏0
  • Swift ABI (二)

    摘要:为了达成二进制层次上的交互这里应该指的是不同版本编译器生成的结果在二进制上兼容,它们必须共享相同的布局协议。例如,对于一个包含个的传统风格来说,它的值用两个就可以表示了数字,,分别对应三个,它们对应二进制的,和。 泊学翻译自Swift在Github上发布的Swift ABI Manifesto Swift ABI的构成 在实践中,ABI关注的内容是紧密耦合在一起的。但是,作为一个概念模...

    Clect 评论0 收藏0
  • swift3学习笔记

    摘要:只将需要改变的值声明为变量。使用或者方法来判断一个合是否是另外一个合的子合或者父合并且两个合并不相等。 一直没有时间好好看一下swift,最近复习了一遍语法,这里记录swift学习过程中遇到的一些问题和要点,和Object-C的一些相关特性这里也不做介绍,只记录swift特有的一些特性swift借鉴了很多语言的语法,特别是脚本语言,在swift里,可以看到python语言的一些影子,还...

    txgcwm 评论0 收藏0

发表评论

0条评论

kidsamong

|高级讲师

TA的文章

阅读更多
最新活动
阅读需要支付1元查看
<