如何从NSMutableArray子类接收通知

时间:2012-03-15 09:56:44

标签: objective-c cocoa nsmutablearray key-value-observing

我已经将NSMutableArray子类化为允许数据源。这称为BaseObjectArray。该数组实际上只包含一个rowid列表(如uint64_t),当请求objectAtIndex时,它会向数据源委托询问具有该rowid的对象(以允许延迟的数据库查询)。

rowid的内部列表本身就是一个类(RowIDSet,或OrderedRowIDSet子类,它只是NSObject的子类),它只维护唯一rowid的列表。

我需要的是以某种方式监听对BaseObjectArray的更改(实际上是通过类似的方法侦听对它的RowIDSet对象的更改)。

由于可以在BaseObjectArray中添加/删除对象而不使用标准的addObject:,而是使用addRowID:,拥有BaseObjectArray的对象可能无法获得标准的KVO通知。

我考虑过的可能解决方案:

  1. BaseObjectArray具有owner和ownerKey属性,而BaseObjectArray触发[owner willChangeForKey:ownerKey];什么都有变化。

  2. 使用will / didChangeNotificationBlocks - 侦听器可以简单地向BaseObjectArray添加一个块(在NSMutableArray中保留这些块),并且当BaseObjectArray中的某些内容发生更改时,将触发此数组中的所有块。我不确定可能发生的保留周期噩梦。

  3. 在BaseObjectArray的'contents'属性上的KVO。任何想要观察BaseObjectArray的人实际上都会观察到keyPath的“内容”,而在BOArray中它会调用[self willChangeForKeyPath:@“contents”]。 contents属性只返回self。

  4. ......显而易见的是我错过了......

  5. 如果其中任何一种产生最大(或任何)意义,或者是否有更好的解决方案,请告诉我。

    谢谢:)

2 个答案:

答案 0 :(得分:3)

除非你知道自己在做什么,否则你应该继承NSMutableArrayNSMutableArray是一个类集群,需要special treatment

为什么不创建一个使用普通NSMutableArray作为其存储类的自定义对象?似乎没有充分的理由在你的案例中继承NSMutableArray,但也许我误解了你的问题。

答案 1 :(得分:0)

我不知道这是否有效,但如果确实如此,那可能是最好的方法。

确保您的NSMutableArray子类与键self符合KVC(如果这对self不起作用,请添加一个新属性,例如rows,它返回自我或自我副本)。要使自己(或您使用的任何新属性)符合KVC,您需要遵循Indexed To-Many Relationship Compliance rules的可变有序集合:

  • 实现一个名为 - 返回数组的方法。
  • 或者有一个名为或_。
  • 的数组实例变量
  • 或者实现方法-countOf以及-objectInAtIndex:或-AtIndexes:。
  • 中的一个或两个。
  • 或者,您也可以实现-get:range:以提高性能。

self勾选第一个方框。也:

  • 实现一个或两个方法-insertObject:inAtIndex:或-insert:atIndexes:。
  • 实现一个或两个方法-removeObjectFromAtIndex:或-removeAtIndexes:。
  • 另外,您还可以实现-replaceObjectInAtIndex:withObject:或-replaceAtIndexes:with:以提高性能

所以你需要例如-insertObject:inSelfAtIndex:-removeObjectFrom<Key>AtIndex:

然后,您可以在任何地方使用manual KVO notifications来通知观察者该对象上的self属性。所以你可以使用

NSIndexSet* indexes = // index set containing the index or indexes of objects to remove
[self willChange: NSKeyValueChangeRemoval valuesAtIndexes: indexes forKey:@"self"];

删除对象时。