Objective-C中的屬性關(guān)鍵字

strong 、weak、copy 、assign 、retain 、unsafe_unretained、readwrite、readonly、atomic、nonatomic

一類是表示原子性(也就是線程安全)的,有atomic和nonatomic,默認(rèn)是atomic,acomic也就是線程安全,但是我們一般都用的nonatomic,因為atomic的線程安全開銷太大,影響性能,即使需要保證線程安全,我們也可以通過自己的代碼控制,而不用atomic。

一類是表示引用計數(shù)的,有assign(iOS5以前用unsafe_unretained),strong,weak,copy。

assign:用于對基本數(shù)據(jù)類型進(jìn)行賦值操作,不更改引用計數(shù)。也可以用來修飾對象,但是,被assign修飾的對象在釋放后,指針的地址還是存在的,也就是說指針并沒有被置為nil,成為野指針。如果后續(xù)在分配對象到堆上的某塊內(nèi)存時,正好分到這塊地址,程序就會crash。之所以可以修飾基本數(shù)據(jù)類型,因為基本數(shù)據(jù)類型一般分配在棧上,棧的內(nèi)存會由系統(tǒng)自動處理,不會造成野指針。

weak:對對象的弱引用,不增加對象的引用計數(shù),也不持有對象,當(dāng)對象消失后指針自動指向nil,所以這里也就防止了野指針的存在。

@interface PropertyTestViewController ()

@property (nonatomic,strong) PropertyTestModel *propertyStrModel;

@property (nonatomic,weak) PropertyTestModel *propertyWeakModel;

@end

self.propertyStrModel = [PropertyTestModel new];

self.propertyWeakModel = self.propertyStrModel;

NSLog(@"%@ %@",self.propertyStrModel,self.propertyWeakModel);

self.propertyStrModel = nil; //銷毀對象

NSLog(@"%@ %@",self.propertyStrModel,self.propertyWeakModel);

strong /?retain:?retain與strong類似是對對象的強(qiáng)引用,會增加對象的引用計數(shù),如果指向了一個空對象,會造成野指針,平常我們用得最多的應(yīng)該也是strong了。

@interface PropertyTestViewController ()

@property (nonatomic,strong) PropertyTestModel *propertyStrModel;

@end

PropertyTestModel *propertyTest = [PropertyTestModel new];

self.propertyStrModel = propertyTest; //引用計數(shù) +1

NSLog(@"%@",self.propertyStrModel);?

propertyTest = nil; //銷毀對象

NSLog(@"%@ ",self.propertyStrModel);

copy:會在內(nèi)存里拷貝一份對象,兩個指針指向不同的內(nèi)存地址。一般用來修飾NSString等有對應(yīng)可變類型的對象,因為他們有可能和對應(yīng)的可變類型(NSMutableString)之間進(jìn)行賦值操作,為確保對象中的字符串不被修改 ,應(yīng)該在設(shè)置屬性是拷貝一份。而若用strong修飾,如果對象在外部被修改了,會影響到屬性。

unsafe_unretained:跟 weak 類似,聲明一個弱引用,但是當(dāng)引用計數(shù)為 0 時,變量不會自動設(shè)置為 nil,現(xiàn)在基本都用weak了。

一類是表示讀寫權(quán)限的,默認(rèn)是readwrite(可讀可寫),還有就是readonly,當(dāng)你希望暴露出來的屬性不能被外界修改時就需要申明為readonly。



assign與weak 的區(qū)別

weak聲明的變量會自動設(shè)置為nil;assign聲明的變量不會自動賦值為nil,容易造成野指針錯誤。

delegate為何要用weak修飾 :?

在ARC環(huán)境下,為避免循環(huán)引用,往往會把delegate屬性用weak修飾;在MRC下使用assign修飾。weak和strong不同的是:當(dāng)一個對象不再有strong類型的指針指向它的時候,它就會被釋放,即使還有weak型指針指向它,那么這些weak型指針也將被清除。

block屬性為什么需要用copy來修飾 ?

因為在MRC下,block在創(chuàng)建的時候,它的內(nèi)存是分配在棧(stack)上的,而不是在堆(heap)上,可能被隨時回收。他本身的作于域是屬于創(chuàng)建時候的作用域,一旦在創(chuàng)建時候的作用域外面調(diào)用block將導(dǎo)致程序崩潰。通過copy可以把block拷貝(copy)到堆,保證block的聲明域外使用。在ARC下寫不寫都行,編譯器會自動對block進(jìn)行copy操作。

__block與__weak的區(qū)別:

__block:在ARC和MRC下都可用,可修飾對象,也可以修飾基本數(shù)據(jù)類型。

__block對象可以在block被重新賦值,__weak不可以。

__weak:只在ARC中使用,只能修飾對象,不能修飾基本數(shù)據(jù)類型(int、bool)。

同時,在ARC下,要避免block出現(xiàn)循環(huán)引用,經(jīng)常會:__weak typedof(self) weakSelf = self;

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

友情鏈接更多精彩內(nèi)容