zoukankan      html  css  js  c++  java
  • Swift3命名空间的实现

    最近在看一些Swift开源库的时候,发现了一些优秀的开源库都使用了命名空间,例如Kingfisher这个开源库中,就针对UIImage,UIImageView,UIButton做了命名空间的扩展。通过logoImageView.kf.setImage(url)这种方式能够很好地避免扩展的命名冲突,而且相对 logoImageView.kf_setImage(url)这种通过前缀避免命名冲突的方式,具有更好的可读性,而且更Swifty化。

    实现原理

    主要通过三点来实现:

    • 泛型类
    • 泛型协议
    • 协议扩展

    分析

    这是演示代码:

    // 定义泛型类
    public final class YKKit<Base> {
        public let base: Base
        public init(_ base: Base) {
            self.base = base
        }
    }
    
    // 定义泛型协议
    public protocol YKKitCompatible {
        associatedtype CompatibleType
        var yk: CompatibleType { get }
    }
    
    // 协议的扩展 
    public extension YKKitCompatible {
        public var yk: YKKit<Self>{
            get { return YKKit(self) }
        }
    }
    
    // 实现命名空间yk
    extension String: YKKitCompatible {}
    
    // String命名空间yk中的函数
    extension YKKit where Base == String {
        // MARK: - Localized
    
        /// 国际化值
        public var localized: String {
            return NSLocalizedString(base, comment: "")
        }
    
    }
    
    // 使用
    let string = "abcd".yk.localized
    
    

    简单解析一下实现代码,主要用到了protocol和generic来实现,而且实现有点绕。

    首先定义一个泛型类YKKit,使用泛型Base

    然后定义支持泛型的协议YKKitCompatible,并通过协议扩展提供协议的默认实现,返回实现泛型类YKKit的对象自身。

    然后对需要实现命名空间的类提供YKKitCompatible协议扩展,并实现相关命名空间的对象方法(主要是扩展新的方法,如代码中的localized方法)。

    整个过程比较绕,主要还是通过协议来划分命名空间,只有遵循协议的类才拥有该命名空间,这可能需要进一步理解。



    作者:星___尘
    链接:https://www.jianshu.com/p/7808aacc0e42
    來源:简书
    简书著作权归作者所有,任何形式的转载都请联系作者获得授权并注明出处。
  • 相关阅读:
    资源放送丨《Oracle存储过程中的性能瓶颈点》PPT&视频
    警示:一个update语句引起大量gc等待和业务卡顿
    周末直播丨细致入微
    Java VS Python:哪个未来发展更好?
    【LeetCode】279.完全平方数(四种方法,不怕不会!开拓思维)
    事件驱动
    Android初级教程以动画的形式弹出窗体
    Android简易实战教程--第五话《开发一键锁屏应用》
    迎战大数据-Oracle篇
    Android初级教程获取手机位置信息GPS与动态获取最佳方式
  • 原文地址:https://www.cnblogs.com/feng9exe/p/9700815.html
Copyright © 2011-2022 走看看