ARC是蘋果為了簡化程序員對內存的管理,推出的一套內存管理機制轴咱,使用ARC機制汛蝙,對象的申請和釋放工作會在運行時,由編譯器自動在代碼中添加retain和release
1> strong:強指針引用的對象朴肺,在生命周期內不會被系統(tǒng)釋放窖剑,在OC中,對象默認都是強指針
2> weak:弱指針引用的對象宇挫,系統(tǒng)會立即釋放苛吱,弱指針可以指向其他已經被強指針引用的對象
他們都是 arc 的東西
ARC的判斷準則:
只要沒有強指針指向對象,就會釋放對象器瘪,弱指針不會這樣翠储,及時有弱指針指向對象,對象沒有強指針指向橡疼,也會自動釋放掉援所。一般,無需顯式聲明為強指針欣除,但是在封裝里住拭,定義方法的時候需要寫明。而弱指針历帚,必須顯式說明滔岳。默認是強指針。
ARC特點
?1> 不允許調用release挽牢、retain谱煤、retainCount
?2> 允許重寫dealloc,但是不允許調用[super dealloc]
?3> @property的參數(shù)
? * strong :成員變量是強指針(適用于OC對象類型)
? * weak :成員變量是弱指針(適用于OC對象類型)
? * assign : 適用于非OC對象類型
?4> 以前的retain改為用strong
oc的指針分2種:
1> 強指針:默認情況下禽拔,所有的指針都是強指針 __strong
2> 弱指針:__weak
在 點m 文件
#import "Dashuai.h"
@implementation Dashuai
- (void)dealloc
{
? ? NSLog(@"對象被銷毀了刘离!");
? ? //[super dealloc];
}
@end
在視圖控制器
@interface ViewController ()
@property (nonatomic, strong) Dashuai? *da;
@end
@implementation ViewController
- (void)viewDidLoad {
? ? [super viewDidLoad];
? ? self.da = [[Dashuai alloc] init];
? ? NSLog(@"調用了 viewdidlowd 方法室叉!");
}
@end
對象不銷毀,da 是強指針對象硫惕。
如果是在方法內部茧痕,聲明的對象(默認都是強指針),那么存在一個聲明周期(局部變量)的問題恼除。方法執(zhí)行完畢踪旷,到關括號完畢,內存也就隨機自動銷毀了缚柳。
- (void)viewDidLoad {
? ? [super viewDidLoad];
? ? Dashuai *dashuai = [[Dashuai alloc] init];
? ? NSLog(@"調用了 viewdidlowd 方法埃脏!");
}
2016-03-08 17:12:33調用了?viewdidlowd?方法!
2016-03-08 17:12:33對象被銷毀了秋忙!
如果換__weak彩掐,那么語句執(zhí)行完畢,立即釋放內存灰追,加斷點課證明
2016-03-08 17:15:41對象被銷毀了堵幽!
再看控件之間,如圖:
視圖控制器強引用 view弹澎,view 強引用了子控件朴下。
[self.view addSubView];//讓 view 對控件強引用
那么這就是以前寫代碼的時候,連線故事板的控件和代碼關聯(lián)的時候苦蒿,總是默認weak的原因殴胧。因為那是視圖控制器在引用子控件,而 view 已經 strong 了佩迟,那么視圖控制器就沒必要 strong团滥。它的內存釋放過程是:
如果程序沒有必要弄強引用,那么就用若引用报强,類比是鏈表灸姊,一條龍,視圖和姿勢圖秉溉,只一個實線連接(父類對象力惯,強引用子類對象之后),其余的引用用?weak虛線召嘶,因為view 已經對子控件強引用了父晶,視圖控制器可以不用?strong。這是蘋果的應用內存管理機制弄跌。當然用?strong 也不是不可以甲喝。
還有之前提到的懶加載
控件的懶加載,是手動的寫類屬性的 set 方法碟绑,進行是否已經加載等的判斷俺猿,避免重復加載的過程。那么手寫 set 格仲,在 viewdidload重寫代碼押袍,就要用 strong 引用,因為是手寫代碼凯肋,那么如果還是 weak 谊惭,在 viewdidload 方法里,使用控件對象侮东,那么一旦執(zhí)行完畢圈盔,立即內存被釋放,因為是 weak 的悄雅。這樣在視圖加載之前驱敲,對象就已經消失了。
強指針與一般意義的智能指針概念相同宽闲,通過引用計數(shù)來記屬錄有多少使用者在使用一個對象众眨,如果所有使用者都放棄了對該對象的引用,則該對象將被自動銷毀容诬。
弱指針也指向一個對象娩梨,但是弱指針僅zd僅記錄該對象的地址,不能通過弱指針來訪問該對象览徒,也就是說不能通過弱專智真來調用對象的成員函數(shù)或訪問對象的成員變量狈定。
1、強指針:默認情況下,所有的指針都是強指針.我們也可以用__strong修飾习蓬。
2纽什、弱指針:用__weak修飾的指針,就是弱指針。
共同點:無論是強指針還是弱指針,都是指針,都可以用來存儲地址.都可以通過這個指針訪問對象的成員區(qū)別:在ARC模式下,他們用來作為回收對象的基準友雳,如果一個對象沒有任何類型的強指針指向的時候,對象就會被自動釋放稿湿。
3、強指針與弱指針的聲明默認情況下,所有的指針都是強類型的.也可以用__strong來標識這個指針是強指針押赊,使用__weak標識指針的類型是弱指針類型的指針饺藤。
4、ARC模式下對象的回收機制沒有強指針指向一個對象的時候.就會被自動回收
5流礁、ARC機制下,屬性的類型是OC對象類型的時候,一般用strong,非OC對象的類型使用assign
6涕俗、ARC機制下的循環(huán)引用問題:當兩個類相互引用作為對方的屬性的時候.在ARC機制下兩邊都用strong就會出現(xiàn)循環(huán)引用,導致內存泄漏,解決辦法:一端用strong,一端用weak
ARC簡單,不用程序員在去管理內存
1.強指針 Strong
2.弱指針 weak
?<都是對象類型下的>
只要有強指針指向一個對象,那么系統(tǒng)就不會回收該對象
只要沒有強指針指向對象,系統(tǒng)“立即”回收該對象
弱指針不會影響對象被回收
默認情況下,所有的指針都是強指針類型
@property(nonatomic,retain)Car * car;
ARC機制 strong 對象,手動內存管理的retain關鍵字,(一定能夠都是應用在對象類型變量上)
ARC機制中的 weak 對象手動內存管理的assign關鍵字,(一定能夠都是應用在對象類型變量上)
* @property (nonatomic,strong)Car * car;//強指針類型的對象,會影響對象回收
* @property (nonatomic,weak)Car * car2;// 弱指針類型的對象,不會影響對象的回收
//@property (nonatomic,assign)Car * car3;//造成迷惑,會導致許多程序員搞不清這個變量到底是stong類型的還是weak類型
@property (nonatomic,strong)NSString * name;
@property (nonatomic,strong)NSString * idCard;
//ARC機制下 "基本數(shù)據類型"的@property參數(shù)使用,與手動內存管理完全一致
@property (nonatomic,assign)int age;//assign僅僅是賦值
下面u附上幾附圖來比較一下強指針和弱指針
強調一些概念
類:是一種結構神帅,它表示對象的類型再姑,對象引用類來獲取和本身有關的各種信息,特別是運行什么代碼來處理每種操作找御。
對象:是一種結構元镀,它包含值和指向其類的隱藏指針绍填。
實例:對象的另一種稱呼。
消息:是對象可以執(zhí)行的操作栖疑,用于通知對象去做什么讨永。對象接收消息后,將查詢對應的類遇革,以便查找正確的代碼來運行卿闹。
方法:是為響應消息而運行的代碼,根據對象的類萝快,消息可以調用不同的方法锻霎。
接口:是對象的類應該提供特殊的特性的描述。
什么是property揪漩?
property是一種代碼生成機制旋恼,能夠生成不同類型的getter/setter函數(shù),特別是如果你想要用點(.)操作符號來存取變量的話氢拥,你就能必須使用property蚌铜。
oc中訪問成員變量的四種方式
用法如:@property (attribute1,attribute2) float value;這些attribute包括:
readonly? 表示這個屬性是只讀的,就是只生成getter方法嫩海,不會生成setter方法冬殃。
readwrite?可讀可寫(默認)設置可訪問級別。 ??
assign:簡單賦值叁怪,不更改索引計數(shù)對基礎數(shù)據類型(NSInteger)和C數(shù)據類型(int ,float,double,char等审葬。 ?
??copy:建立一個索引數(shù)為1的對象,然后釋放舊對象retain 到另一個NSString之后奕谭,地址相同(建立一個指針涣觉,指針拷貝),內容當然相同血柳,這個對象的retain值+1官册,也就是說,retain是指針拷貝难捌,copy是內容拷貝膝宁。在拷貝之前,都會釋放舊的對象根吁。?
? ?nonatomicnonatomic?非原子性訪問员淫,不加同步,多線程并發(fā)訪問會提高性能击敌。注意介返,如果不加此屬性, 則默認是兩個訪問方法都為原子型事務訪問。前兩個只是簡單的設定變量的可讀寫性圣蝎。
@class
1 在Objective-c中刃宵,當一個類使用到另一個類,并且在類的頭文件中需要創(chuàng)建被引用的指針時徘公,一般有繼承關系的用#import组去;沒有繼承關系的話,可以在頭文件中使用@class步淹,聲明類,這樣可以提高編譯效率诚撵。在大型軟件中缭裆,減少.h文件中的include頭文件,提高編譯效率是非常重要的寿烟。
一種是通過#import方式引入澈驼;另一種是通過@class引入
為了簡單起見:A類是引用類,B類是被引用類筛武,這里先不考慮A類的實現(xiàn)文件缝其。
#import?"B.h"????
@interface?A?:?NSObject?{ ??
????B?*b; ??
} ??
@end??
這兩種的方式的區(qū)別在于:
1、#import方式會包含被引用類的所有信息徘六,包括被引用類的變量和方法内边;@class方式只是告訴編譯器在A.h文件中?B *b?只是類的聲明,具體這個類里有什么信息待锈,這里不需要知道漠其,等實現(xiàn)文件中真正要用到時,才會真正去查看B類中信息竿音;
2和屎、使用@class方式由于只需要只要被引用類(B類)的名稱就可以了,而在實現(xiàn)類由于要用到被引用類中的實體變量和方法春瞬,所以需要使用#import來包含被引用類的頭文件柴信;
3、通過上面2點也很容易知道在編譯效率上宽气,如果有上百個頭文件都#import了同一 個文件随常,或者這些文件依次被#improt(A->B, B->C,C->D…),一旦最開始的頭文件稍有改動,后面引用到這個文件的所有類都需要重新編譯一遍抹竹,這樣的效率也是可想而知的线罕,而相對來 講,使用@class方式就不會出現(xiàn)這種問題了窃判;
4钞楼、對于循環(huán)依賴關系來說,比方A類引用B類袄琳,同時B類也引用A類询件,需要使用@class燃乍,否則會報錯。
2@class Dog;//當一個類使用到另一個類時宛琅,并且在類的頭文件中需要創(chuàng)建被引用的指針時刻蟹。需要在頭文件中引用@class 它類名 如:person類引入dog類對象
3@interfacePerson : NSObject
4@property(nonatomic,strong) Dog *dog;
1#import"Person.h"
2 #import "Dog.h"
3@implementation Person :NSObject
總結一下
@class是放在interface中的,只是為了在interface中引用這個類嘿辟,把這個類作為一個類型來用的舆瘪。 在實現(xiàn)這個接口的實現(xiàn)類中,如果需要引用這個類的實體變量或者方法之類的红伦,還是需要import在@class中聲明的類進來.?
@property參數(shù)詳解
1>strong :強指針(適用于oc對象類型)
2>weak ?:弱指針(適用于oc對象類型)
3>assign:適用于基本數(shù)據類型(即非OC對象類型)
ARC (?iOS 5推出的新功能,全稱叫 ARC(Automatic Reference Counting)自動引用計數(shù))
ARC的判斷準則:只要沒有強指針指向對象英古,就會釋放對象
? ? a)在ARC機制中,所有的retain昙读,release都不能再出現(xiàn)召调,取而代之的則是strong(強指針)和weak(弱指針)
????b)默認情況下,所有的指針都是強指針類型
????c)只要有強指針指向一個對象,那么系統(tǒng)就不會回收該對象;反之蛮浑,則立即回收該對象
@property中的strong和weak屬性
? ? a)arc中的strong相當于非arc時的retain
????b)arc中的weak相當于非arc時的assign
????c)arc機制情況下不能再出現(xiàn) [super dealloc];
????d)基本數(shù)據類型依然使用assign修飾唠叛,對象一般用strong修飾
????e)當arc機制下對象循環(huán)依賴時,這時weak就有用處沮稚,結合@class艺沼。否則都是strong對方會相互拉著對方,釋放不了內存
OC中ARC機制中還有內存泄漏嗎
基于計數(shù)的內存管理是無法處理循環(huán)引用的蕴掏,這和自動不自動沒有關系澳厢。
另外不管用什么管理方式都解決不了,其實對象已經沒用了但是忘了撒手”的bug。
比如即便你沒循環(huán)引用囚似,但是有一個生存期很長的變量保存著一個根本沒用的對象的引用還是會泄露的剩拢。基于xcode arc機制 只要不影響程序性能編程并不關心饶唤。
參考鏈接:
https://blog.csdn.net/u011146511/article/details/51527090
https://www.cnblogs.com/wxios/articles/4175468.html
http://www.reibang.com/p/d8ae167e0cc5
著作權歸作者所有徐伐。商業(yè)轉載請聯(lián)系作者獲得授權。