每次在Objective-C(Cocoa)上设置参数时调用方法

时间:2012-06-11 19:54:17

标签: objective-c xcode cocoa xcode4

我目前有一个包含15个属性(并且还在增长)的类,并且每当其中一个属性发生变化时,我发现自己必须调用更新方法。

目前,我用这样的代码覆盖每个setter:

-(void)setParameterName:(NSUInteger)newValue {
  if (_param == newValue)
    return;
  _param = newValue;
  [self redraw];
}

方法 [self redraw]; 是关键。

有更好的方法吗?我应该使用keyValue观察者(方法observeValue:forKeyPath:ofObject:change:context:)?

注意:

  • 所有属性(目前为止)都是 assign (主要是enumNSUIntegerCGFloatBOOL); < / LI>
  • 所有这些属性都是使用绑定设置的(方法bind:toObject:withKeyPath:options:)。从文件系统加载时除了(这不重要,因为我在加载完成后已经在每个对象上调用了绘图方法);
  • 值更改仅适用于当前对象。我不需要被告知其他对象何时发生变化;
  • 我有其他属性,我不需要观察它的变化(因为它对我的输出没有影响,绘制输出有点费时)。

谢谢!

2 个答案:

答案 0 :(得分:2)

由于这些属性是使用调用-setValue:forKey:的绑定更新的,因此您可以覆盖该方法而不是编写自定义setter:

+ (NSArray *) keysAffectingDrawing {
    static NSArray *singleton;
    if (!singleton)
        singleton = [NSArray arrayWithObjects:
                      @"property1",
                      @"property2",
                      @"property3",
                      nil];
    return singleton;
}

- (void) setValue:(id) value forKey:(NSString *) key {
    [super setValue:value forKey:key];
    if ([[CustomClass keysAffectingDrawing] containsObject:key]) [self redraw];
}

(我首先倾向于推荐键值观察,但同意它不是这里的最佳解决方案。我认为原因部分是只有一个对象,部分原因是设计不遵循MVC。通常在MVC中绘制自身的对象不是具有所有属性的对象。)

添加:啊,我明白了。模型负责将属性呈现给位图,这就是-redraw所做的。这是很好的MVC。为了让它更清晰,我建议将方法名称从-redraw更改为-updateImage-renderImage,因为它实际上不会进行任何绘图。)

答案 1 :(得分:1)

您可以使用Key-Value Observing来避免在所有属性中重复设置方法调用,但是我认为直接在setter中调用方法并不是错误的方法,甚至可能更快.. 。