iOS 中属性与方法的访问权限等级
在 Xcode 中共有五种对变量和方法的访问权限, 其等级从低到高依次是:
private
fileprivate
internal
public
open
五种等级 (由低到高)
private
只在本文件且本类 (或本类扩展) 中可以被访问
- 如果在一个文件中且任何类外声明一个
private
属性, 那么该属性可被该文件所有位置访问到, 但是外部文件不能访问到此属性 - 如果将类中某个属性
abc
设为private
, 在其他文件中对该类进行extension
, 那么在该extension
中是不能被访问到abc
的
fileprivate
只在本文件中可以被访问
如果一个文件中有两个及以上的类的话, 那么被 fileprivate
标记的类中的属性就可以在本文件的多个类中被访问, 而被 private
访问的就只能在本文件的本类 extension
中被访问
对于 top level 的 类 / 方法 / 变量来说, 使用 fileprivate 或 private 没有区别
internal
本模块内可以使用
xcode
默认使用本种权限, cocoapods
即一个单独的模块 module
public
本项目中各 module
任意读取, 不能在其他 module
中继承重写. 框架, api, 库中经常用, 个人开发少用
open
本项目中各 module
任意读取, 重写, 继承
对 getter 与 setter 设置不同的访问级别
// 把 getter 设为 public 级别, setter 设为 private 级别
public private(set) var disposeBag = DisposeBag()
// 把 getter 设为默认的 internal 级别, setter 设为 private 级别
private(set) var name: String?
迪米特法则与实践
迪米特法则(LoD, Law of Demeter), 如果一个类知道了太多不属于它本身的内容, 则代表这个类与外部的耦合程度越高, 越不灵活, 越难以复用. 但是如果这个类完全不知道外部信息, 那么物件之间也无法合作, 整个应用也就无法运行. 因此我们要保证每个类对外界开放最少的属性, 拥有对外界最少的知识, 这样既可以确保物件之间的合作, 也较灵活, 便于复用与解耦
law 的意思是法则, 比原则 principle 要强势的多. 在 principle 的世界中, 如果两个 principle 之间有所抵触, 那么我们会衡量彼此的价值, 然后取其中地位较高的, 也就是说 principle 之间是可以相互妥协的, 但是 law 就不是这样的, 他代表一种绝对的法则, 没有什么可以撼动 Lod 的地位.
iOS 开发中, 因为 Swift 语言对于声明的属性是 internal 级别的, 这样并不能保证每个类的最少暴露. 我的建议是养成在定义方法或者属性的时候手动添加 private
或 fileprivate
的习惯, 这样长此以往我们可以将这些经典的设计模式融入到我们的骨髓中.
我一直在想为什么 Swift 不将默认的级别设为
private
, 而是设为模块内均可以访问的internal
, 现在我的看法是 Swift 为了让基础差的人容易上手, 更容易接受.
本博客文章采用 CC 4.0 协议,转载需注明出处和作者。