声明的属性
当编译器遇到属性声明时(请参阅Objective-C编程语言中的声明属性),它会生成与封闭类,类别或协议相关联的描述性元数据。您可以在类或协议上按名称查找属性,将属性类型作为@encode
字符串获取,以及将属性列表作为C字符串数组复制的函数来访问此元数据。每个类和协议都有一个声明的属性列表。
属性类型和功能
该Property
结构定义了属性描述符的不透明句柄。
typedef struct objc_property *Property;
您可以使用这些函数class_copyPropertyList 和 protocol_copyPropertyList
分别检索与类关联的属性数组(包括已加载的类别)和协议:
objc_property_t *class_copyPropertyList(Class cls, unsigned int *outCount)
objc_property_t *protocol_copyPropertyList(Protocol *proto, unsigned int *outCount)
例如,给定以下类声明:
@interface Lender : NSObject {
float alone;
}
@property float alone;
@end
您可以使用以下方式获取属性列表:
id LenderClass = objc_getClass("Lender");
unsigned int outCount;
objc_property_t *properties = class_copyPropertyList(LenderClass, &outCount);
您可以使用该property_getName
函数来发现属性的名称:
const char *property_getName(objc_property_t property)
您可以使用这些函数class_getProperty
并protocol_getProperty
分别获取对类和协议中具有给定名称的属性的引用:
objc_property_t class_getProperty(Class cls, const char *name)
objc_property_t protocol_getProperty(Protocol *proto, const char *name, BOOL isRequiredProperty, BOOL isInstanceProperty)
您可以使用该property_getAttributes
函数来发现@encode
属性的名称和类型字符串。有关编码类型字符串的详细信息,请参阅类型编码 ; 有关此字符串的详细信息,请参阅属性类型字符串和属性属性描述示例。
const char *property_getAttributes(objc_property_t property)
将这些放在一起,您可以使用以下代码打印与类关联的所有属性的列表:
id LenderClass = objc_getClass("Lender");
unsigned int outCount, i;
objc_property_t *properties = class_copyPropertyList(LenderClass, &outCount);
for (i = 0; i < outCount; i++) {
objc_property_t property = properties[i];
fprintf(stdout, "%s %s\n", property_getName(property), property_getAttributes(property));
}
属性类型字符串
您可以使用该property_getAttributes
函数来发现名称,@encode
属性的类型字符串以及属性的其他属性。
该字符串以a开头,T
后跟@encode
类型和逗号,并以a 结尾,后跟V
后备实例变量的名称。在这些属性之间,属性由以下描述符指定,用逗号分隔:
Table 7-1 | |
---|---|
Declared property type encodings | |
Code | Meaning |
R | The property is read-only (readonly ). |
C | The property is a copy of the value last assigned (copy ). |
& | The property is a reference to the value last assigned (retain ). |
N | The property is non-atomic (nonatomic ). |
G<name> | The property defines a custom getter selector name. The name follows the G (for example, GcustomGetter, ). |
S<name> | The property defines a custom setter selector name. The name follows the S (for example, ScustomSetter:, ). |
D | The property is dynamic (@dynamic ). |
W | The property is a weak reference (__weak ). |
P | The property is eligible for garbage collection. |
t<encoding> | Specifies the type using old-style encoding. |
有关示例,请参见属性属性描述示例。
属性属性描述示例
鉴于这些定义:
enum FooManChu { FOO, MAN, CHU };
struct YorkshireTeaStruct { int pot; char lady; };
typedef struct YorkshireTeaStruct YorkshireTeaStructType;
union MoneyUnion { float alone; double down; };
下表显示了示例属性声明和返回的相应字符串property_getAttributes
:
Property declaration | Property description |
---|---|
@property char charDefault; | Tc,VcharDefault |
@property double doubleDefault; | Td,VdoubleDefault |
@property enum FooManChu enumDefault; | Ti,VenumDefault |
@property float floatDefault; | Tf,VfloatDefault |
@property int intDefault; | Ti,VintDefault |
@property long longDefault; | Tl,VlongDefault |
@property short shortDefault; | Ts,VshortDefault |
@property signed signedDefault; | Ti,VsignedDefault |
@property struct YorkshireTeaStruct structDefault; | T{YorkshireTeaStruct="pot"i"lady"c},VstructDefault |
@property YorkshireTeaStructType typedefDefault; | T{YorkshireTeaStruct="pot"i"lady"c},VtypedefDefault |
@property union MoneyUnion unionDefault; | T(MoneyUnion="alone"f"down"d),VunionDefault |
@property unsigned unsignedDefault; | TI,VunsignedDefault |
@property int (*functionPointerDefault)(char *); | T^?,VfunctionPointerDefault |
Note: the compiler warns: | T@,VidDefault |
@property int *intPointer; | T^i,VintPointer |
@property void *voidPointerDefault; | T^v,VvoidPointerDefault |
In the implementation block:
| Ti,V_intSynthEquals |
@property(getter=intGetFoo, setter=intSetFoo:) int intSetterGetter; | Ti,GintGetFoo,SintSetFoo:,VintSetterGetter |
@property(readonly) int intReadonly; | Ti,R,VintReadonly |
@property(getter=isIntReadOnlyGetter, readonly) int intReadonlyGetter; | Ti,R,GisIntReadOnlyGetter |
@property(readwrite) int intReadwrite; | Ti,VintReadwrite |
@property(assign) int intAssign; | Ti,VintAssign |
@property(retain) id idRetain; | T@,&,VidRetain |
@property(copy) id idCopy; | T@,C,VidCopy |
@property(nonatomic) int intNonatomic; | Ti,VintNonatomic |
@property(nonatomic, readonly, copy) id idReadonlyCopyNonatomic; | T@,R,C,VidReadonlyCopyNonatomic |
@property(nonatomic, readonly, retain) id idReadonlyRetainNonatomic; | T@,R,&,VidReadonlyRetainNonatomic |
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论