为什么 __weak 对象会被添加到自动释放池?
Why __weak object will be added to autorelease pool?
id __weak obj1 = obj0;
等于
id __weak obj1 = obj0;
id __autoreleasing tmp = obj0;
在 iOS 和 OSX 的 Pro 多线程和内存管理中。
但是为什么obj1
需要添加到自动释放池中,我认为做一个对象的弱指针应该不会影响它的生命周期。
{
NSObject* sp = [NSObject new];
NSObject* __weak wp = sp;
}
以上代码翻译为:
id sp = objc_msgSend(NSObject, "new");
id wp;
objc_initWeak(&wp, sp);
objc_destroyWeak(&wp);
objc_storeStrong(&sp, 0);
1) obj_initWeak
只是将弱指针wp
与强指针sp
关联起来,确保sp
指向的对象被释放时wp
会自动重置为 nil,这不会增加指向对象的保留计数。
2)obj_destroyWeak
破坏弱指针与强指针的关联
3)最后一个语句中的obj_storeStrong
等于[sp release]
.
但是一旦我们使用弱指针,编译器就会为指向的对象生成一个新的引用。
{
NSObject* sp = [NSObject new];
NSObject* __weak wp = sp;
NSLog(@"%@", wp);
}
变成
id sp = objc_msgSend(NSObject, "new");
id wp;
objc_initWeak(&wp, sp);
id tmp = objc_loadWeakRetained(wp);
NSLog(@"%@", wp);
objc_release(tmp);
objc_destroyWeak(&wp);
objc_storeStrong(&sp, 0);
objc_loadWeakRetained
会增加引用计数以确保 tmp
在 NSLog
语句中处于活动状态。
objc_release
将对象重置为原始状态。
综上所述,__weak
的这种设计保证了弱指针在使用过程中,其状态是一致的。 Apple LLVM version 8.0.0 (clang-800.0.42.1)
的__weak
的新实现没有延迟发布到autoreleasepool
,而是直接使用objc_release
。
id __weak obj1 = obj0;
等于
id __weak obj1 = obj0;
id __autoreleasing tmp = obj0;
在 iOS 和 OSX 的 Pro 多线程和内存管理中。
但是为什么obj1
需要添加到自动释放池中,我认为做一个对象的弱指针应该不会影响它的生命周期。
{
NSObject* sp = [NSObject new];
NSObject* __weak wp = sp;
}
以上代码翻译为:
id sp = objc_msgSend(NSObject, "new");
id wp;
objc_initWeak(&wp, sp);
objc_destroyWeak(&wp);
objc_storeStrong(&sp, 0);
1) obj_initWeak
只是将弱指针wp
与强指针sp
关联起来,确保sp
指向的对象被释放时wp
会自动重置为 nil,这不会增加指向对象的保留计数。
2)obj_destroyWeak
破坏弱指针与强指针的关联
3)最后一个语句中的obj_storeStrong
等于[sp release]
.
但是一旦我们使用弱指针,编译器就会为指向的对象生成一个新的引用。
{
NSObject* sp = [NSObject new];
NSObject* __weak wp = sp;
NSLog(@"%@", wp);
}
变成
id sp = objc_msgSend(NSObject, "new");
id wp;
objc_initWeak(&wp, sp);
id tmp = objc_loadWeakRetained(wp);
NSLog(@"%@", wp);
objc_release(tmp);
objc_destroyWeak(&wp);
objc_storeStrong(&sp, 0);
objc_loadWeakRetained
会增加引用计数以确保 tmp
在 NSLog
语句中处于活动状态。
objc_release
将对象重置为原始状态。
综上所述,__weak
的这种设计保证了弱指针在使用过程中,其状态是一致的。 Apple LLVM version 8.0.0 (clang-800.0.42.1)
的__weak
的新实现没有延迟发布到autoreleasepool
,而是直接使用objc_release
。