9

我对Objective C很陌生。(现在两天)。阅读时@synthesize,它似乎与我的理解重叠@property(我以为我理解)......所以,一些细节需要在我的脑海中解决......这让我很烦恼。

如果我对@property和的差异有误,请纠正我@synthesize

如果您在 中声明 a @property@interface那么您就是在告诉全世界用户可以期望对该属性使用标准的 getter 和 setter。此外,XCode 将为您制作通用的 getter 和 setter。 ...但是,@property 声明会在多大程度上发生这种情况?(IE 是否意味着“完全”......就像你的看不见的声明@interface,以及你的看不见的代码@interface

-或者-

是否@property处理您唯一的看不见的代码声明@interface- 而@synthesize处理您部分中看不见的代码实现@implementation?)

4

3 回答 3

17

首先,请注意最新版本的 Xcode 不再需要 @synthesize。您可以(并且应该)忽略它。也就是说,这就是这些碎片的作用。

@property是访问者的声明。这只是一个声明。以下之间几乎没有区别:

@property (nonatomic, readwrite, strong) NSString *something;

对比

- (NSString *)something;
- (void)setSomething:(NSString)aSomething;

主要区别在于使用声明这些方法@property让编译器自动为您生成(综合)实现。没有要求您让编译器为您做这件事。您完全可以自由地手动实施somethingsetSomething:这很常见。但是,如果您不手动实现它们,编译器会自动为您创建一个 ivar,_something并为 getter 和 setter 创建一个合理的实现。

在旧版本的 Xcode 中,您必须使用@synthesize关键字显式请求自动生成。但这不再需要。今天,使用的唯一原因@synthesize是如果您希望 ivar 具有非标准名称(永远不要这样做)。

这里的一个关键点是 methodssomethingsetSomething:are just methods。他们没有什么神奇的。它们不是特殊的“属性方法”。它们只是按照惯例访问一个状态的方法。该状态通常存储在 ivar 中,但不需要。

更清楚一点:object.something并不意味着_something“从object.返回命名的 ivar ”。它的意思是“返回 的结果[object something],不管它做什么。” 返回 ivar 的值是很常见的。

您应该使用声明来声明所有状态(内部和外部)@property,并且应该避免直接声明 ivars。您还应该始终通过它们的访问器 ( self.something) 访问您的属性,除了initanddealloc方法。在initanddealloc中,您应该直接使用 ivar ( _something)。

于 2012-10-04T15:19:25.940 回答
7

@property使用您提供的任何原子性和 setter 语义在您的类上声明一个属性。

在 Xcode 4.4 中,可以使用自动合成,其中为您提供了来自您的属性的支持 ivar,而无需在@synthesize. 此 ivar 的形式为_propertyNamewhere your property name is propertyName

于 2012-10-04T15:12:08.310 回答
0

Objective-C @property 和 @synthesize

@property

  • 生成 get/set 方法
  • 今天(来自 Xcode v4.4 和 LLVM v4.0)@property另外使用@synthesizeinside
    • @synthesize propertyName = _propertyName

@synthesize

  • 生成新的 iVar 或与现有 iVar 的链接
  • 使用适当的 iVar 生成 get/set 方法的实现

[可以使用@synthesize 的情况]

@property

@interface SomeClass : NSObject
@property NSString *foo;
@end

//generated code
@interface SomeClass : NSObject
- (NSString *)foo;
- (void)setFoo:(NSString)newFoo;
@end

@synthesize图案

@synthesize <property_name> = <variable_name>;

//Using
//1. Specify a variable. New variable(variableName) will be generated/linked with existing
@synthesize propertyName = variableName

//if variableName is not exist it generates: 
//NSString *variableName;

//read access
NSString *temp = variableName;

//2. Default. New variable(propertyName - the same name as a property) will be generated/linked with existing
@synthesize propertyName
//is the same as
//@synthesize propertyName = propertyName

//if propertyName is not exist it generates:  
//NSString *propertyName;

//read access
NSString *temp = propertyName;

//if you specify not-existing <property_name>  you  get
//Property implementation must have its declaration in interface '<class_name>' or one of its extensions

以前您必须使用下一个语法:

@interface SomeClass : NSObject
{
    //1. declare variable
    NSString *_foo;
}
//2. create property
@property NSString *foo;
@end

@implementation SomeClass
//3. link property and iVar
@synthesize foo = _foo;
@end

但是今天你可以使用下一个语法

@interface SomeClass : NSObject
//1. create property
@property NSString *foo;
@end

接下来,将为两种情况生成相同的代码

@interface SomeClass : NSObject
{
    //variable
    NSString *_foo; 
}

//getter/setter
- (void)setFoo:(NSString *)newFoo;
- (NSString *)foo;
@end

@implementation SomeClass
- (void)setFoo:(NSString *)newFoo
{
    _foo = newFoo;
}
- (NSString *)foo
{
    return _foo;
}
@end
于 2021-05-16T21:36:57.087 回答