自定义设置为@property?

我在合成后如何使用自定义的setter来获得以下属性?

@property (nonatomic,retain) UIButton *but 

 @property (getter=yourGetter,setter=yourSetter:) UIButton *but; 

@Sascha几乎是正确的,但他的代码中有一个小错误;)

它看起来像是:

一个)

 -(void)setBut:(UIButton *)value { if (but != value) { [but release]; but = [value retain]; } } 

或B)

 -(void)setBut:(UIButton *)value { [but autorelease]; but = [value retain]; } 

(A)(非常)更有效率,(B)更可读。


为什么我们需要选项(A)中的if语句,而不是仅在@ Sascha的答案中发布和保留?

如果你两次传入同一个对象会发生什么?

 // We set our button for the first time UIButton *test = [UIButton alloc] init]; [self setBut:test]; [test release]; // Much later in the code, we set the button again [self setBut:test]; 

如果我们没有检查, but不是一个不同的对象,我们在setter中做的第一件事是release它。 然后我们会试图retain一个不存在的对象,导致崩溃。

注意我们不需要选项(B)中的if语句,因为autorelease不会立即释放button,所以我们有时间再次保留它,而不会被释放。

B +)替代deanWombourne解决scheme:

 -(void)setBut:(UIButton *)value { [value retain] [but release]; but = value; } 

这个解决scheme将防止价值是一个子对象的问题。

A +)替代deanWombourne解决scheme:

 -(void)setBut:(UIButton *)value { if (but != value) { [value retain] //insert here but's cancel, invalidate, delegate = nil, ... [but release]; but = value; } } 

这个解决scheme将防止价值是一个子对象的问题。 它将允许你添加一个NSURLConnection的cancel ,一个NSTimer或NSPort invalidate ,一个委托的零,…

实行

 - (void)setBut:(UIButton *)aButton; 

它应该看起来像

 - (void)setBut:(UIButton *)aButton { [but release]; but = [aButton retain]; // whatever } 

我相信这是@synthesised制定者如何去做的,而且它在任何情况下都能正常工作,不pipe你是否指定了同一个对象:

 - (void)setBut: (UIButton*)aButton { id oldObject = but; but = [aButton retain]; [oldObject release]; } 

据我所知,不能出错。