簡體   English   中英

從什么時候開始在類別中聲明Objective-C 2.0屬性?

[英]Since when is it possible to declare Objective-C 2.0 properties in a category?

我一直認為不能在類別中聲明對象屬性。 直到我的合作伙伴在我們的應用程序代碼中完成它,它似乎工作。

我繼續SO和谷歌狂熱試圖向他解釋不,Objective-C類別只能用於添加方法,而不是屬性。 我發現了諸如以下問題:

但后來我在Apple的網站上發現了這個鏈接 ,其中包含有關@property聲明的以下內容:

屬性聲明以關鍵字@property開頭。 @property可以出現在類的@interface中找到的方法聲明列表中的任何位置。 @property 也可以出現在協議或類別的聲明中 (重點補充)

我知道這不起作用:

@interface MyClass ()
NSInteger foobar;
- (void) someCategorizedMethod;
@end

但這編譯:

@interface MyClass ()
@property NSInteger foobar;
- (void) someCategorizedMethod;
@end

我的問題是(a)這里的最佳做法是什么? (b)這是Objective-C 2.0的新功能,而不是使用“真正的”iVar,它只是在幕后使用關聯存儲來實現這個功能嗎?

您始終可以在類別中聲明@property 你不能做的 - 現在仍然不能 - 為類別中的屬性聲明存儲,既不作為實例變量也不通過`@synthesize。

然而....

@interface MyClass () 不是一個類別 它是類擴展,具有明顯比類別更具體的角色。

也就是說,類擴展可用於擴展類的@interface ,這包括可以@synthesized的@properties(包括在現代運行時中合成存儲)。

Foo.h:

@interface Foo
@end

Foo.m:

@interface Foo()
@property int x;
@end

@implementation Foo
@synthesize x; // synthesizes methods & storage
@end

它只是在幕后使用關聯存儲來完成這項工作?

不 - 它是一個真實的實例變量。 現代運行時修復了脆弱的基類問題。


@interface MyClass ()
NSInteger foobar;
- (void) someCategorizedMethod;
@end

上述方法不起作用(如預期的那樣),因為foobar實際上是一個全局變量。

如果您將其更改為:

@interface MyClass () {
    NSInteger foobar;
}
- (void) someCategorizedMethod;
@end

然后它將使用最新版本的llvm編譯器(帶有正確的標志,如@Joshua在評論中指出的那樣)。

Assotiative存儲是解決方案。 看看這篇文章

一般來說,屬性與其他方法沒有什么不同。 只要普通類中使用的ivar,就沒有任何問題。 這只是語法糖。

如果自動創建ivar,事情開始變得更加困難,在某些配置中也是如此。

這里的要點是伊薩爾的宣言獨立於財產。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM