由于什么时候可以在一个类别中声明Objective-C 2.0属性? [英] Since when is it possible to declare Objective-C 2.0 properties in a category?

查看:61
本文介绍了由于什么时候可以在一个类别中声明Objective-C 2.0属性?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我一直认为不能在类别中声明对象属性。
,直到我的伴侣在我们应用程序的代码中完成操作为止,它似乎仍然起作用。

I always thought that one cannot declare an object property in a category. Until my partner did it in our app's code, and it seemed to work.

我继续进行搜索操作,然后Google狂饮向他解释不,Objective-C类别只能用于添加方法,不能用于属性。我发现了以下问题:

I went on a SO and Google binge to try to explain to him that no, Objective-C categories can only be used to add methods, not properties. I found questions such as:

  • Setting New Property In Category Interface Implementation (look at the accepted answer)
  • Can I add a property for a method not in my category?

但是后来我发现此链接包含以下内容: @property声明:

But then I found this link on Apple's site that contains the following about the @property declaration:


属性声明以
关键字@property开头。 @property可以使
出现在类的
@接口中的方法
声明列表中的任何位置。 @property
还会出现在
协议或类别的声明中吗
。 (强调)

我知道这行不通:

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

但这会编译:

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

我的问题是(a)此处的最佳做法是什么? (b)这是Objective-C 2.0的新功能,而不是使用真实的 iVar,而只是使用幕后的关联存储来完成这项工作?

My question is (a) what's the best practice here? and (b) is this something that is new to Objective-C 2.0, and instead of using a "real" iVar, it simply uses associative storage behind the scenes to make this work?

推荐答案

您始终可以在类别中声明 @property 。您不能做,而且仍然不能做的是,声明该类别中属性的存储,既不作为实例变量也不通过`@synthesize声明。

You have always been able to declare an @property in a category. What you couldn't do -- and still can't -- is declare storage for the property in the category, neither as an instance variable nor via `@synthesize.

但是....

@interface MyClass()不是类别 。它是一个类扩展,并且比类别具有明显更具体的作用。

@interface MyClass () is not a category. It is a class extension and has a distinctly more specific role than a category.

即,类扩展可用于扩展类的@interface ,其中包括可以@合成的@properties(包括在现代运行时中合成存储)。

Namely, a class extension can be used to extend a class's @interface, and this includes @properties that can be @synthesized (including synthesizing storage in the modern runtime).

Foo.h:

@interface Foo
@end

Foo.m:

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

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




它只是使用关联存储
在幕后才能完成这项工作?

it simply uses associative storage behind the scenes to make this work?

不是-这是一个真实的实例变量。现代的运行库解决了脆弱的基类问题。

Nope -- it is a real instance variable. The modern runtime fixes the fragile base class problem.

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

上述操作无效(按预期),因为 foobar 实际上是一个全局变量。

The above doesn't work (as expected) because foobar is, effectively, a global variable.

如果将其更改为:

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

然后,它将与最新版本的llvm编译器(带有正确的标志,如@Joshua在评论中指出的。)

Then it'll work with the latest release of the llvm compiler (with the right flags, as @Joshua indicated in a comment).

这篇关于由于什么时候可以在一个类别中声明Objective-C 2.0属性?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆