oc懒加载
oc懒加载机制充分使用了oc点语法的特性。举个例子
@interface MyView()
@property (nonatomic, strong) UIView *view;
@end
@implementation MyView
- (instancetype)init {
if (self = [super init]) {
[self constructSubviews];
}
return self;
}
- (void) constructSubviews {
[self addSubview:self.view];
}
- (UIView *)view {
if (nil == _view) {
_view = [[UIView alloc] init];
}
return _view;
}
@end
上面这个例子定义了view属性,当MyView被创建的时候并没有立马对view属性进行初始化,当代码执行到[self addSubview:self.view]
的时候,view属性被首次使用,self.view会去执行view属性的get方法,首次使用的时候_view == nil
,所以会进入if条件分支创建view,当下次再次通过点语法访问view的时候(self.view),再次进入get方法,而这个时候将不再进入条件分支,将之前创建好的对象直接返回,这就是oc懒加载的机制。
swift懒加载
swift中有个关键字lazy,通过lazy修饰成员变量使之具有懒加载特性。举个例子
class ViewController: UIViewController {
lazy var view: UIView = UIView()
override func viewDidLoad() {
super.viewDidLoad()
print(view)
print(view)
view = nil
print(view)
}
}
上面这个例子ViewController被创建的时候成员变量view并不会被创建,当执行print(view)
的时候,view首次被使用,这个时候才会真正的被创建,当再次执行print(view)
,可以看出他们的内存地址是一样的,从而证明他们是同一个对象,当给view设置为nil后再去使用view的话,view将不在重新创建,这点和OC懒加载不同,oc是通过点语法,设置nil后,再次通过点语法去取值,会重新进入get方法中的条件分支重新分配新的内存创建一个新的对象。
综上可以得出一个结论,swift懒加载只会在首次使用的时候创建一次,之后再次使用或者新赋值都不会去重新创建了,而是就保存新设置的值。
swift懒加载的写法举例
lazy var tLabel: TestLabel = TestLabel() // 通过构造函数初始化
lazy var tLabel: TestLabel = TestLabel.creatTesstLabel() // 通过类方法创建(也可通过对象调方法创建)
// 通过匿名方法(闭包)创建
lazy var tLabel: TestLabel = {
let l = TestLabel()
// 设置label属性....
return l
}()
lazy var tLabel = { () -> TestLabel in
let l = TestLabel()
// 设置label属性....
return l
}()
总之结论就是等号后面的代码能返回和变量类型匹配的值