我应该如何处理来自kvo的NSIndexSet来更新表格视图?

时间:2011-06-04 14:31:09

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

我开始使用键值观察,我正在观察的可变数组在更改字典中给出了NSIndexSets(Ordered mutable to-many)。问题是表格视图,据我所知,我希望我给它NSArrays充满索引。

我考虑过实现一个自定义方法来将一个方法转换为另一个,但这似乎很慢,我得到的印象是,当数组发生变化时,必须有一个更好的方法来使这个表视图更新。

这是来自我的UITableViewDataSource的方法。

 -(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context{
     switch ([[change valueForKey:NSKeyValueChangeKindKey] unsignedIntValue]) {
         case NSKeyValueChangeSetting:
             NSLog(@"Setting Change");
             break;
         case NSKeyValueChangeInsertion:
             NSLog(@"Insertion Change");

             // How do I fit this:
             NSIndexSet * indexes = [change objectForKey:NSKeyValueChangeIndexesKey];

             // into this:
             [self.tableView insertRowsAtIndexPaths:<#(NSArray *)#> withRowAnimation:<#(UITableViewRowAnimation)#>

             // Or am I just doing it wrong?

             break;
         case NSKeyValueChangeRemoval:
             NSLog(@"Removal Change");
             break;
         case NSKeyValueChangeReplacement:
             NSLog(@"Replacement Change");
             break;
         default:
             break;
     }
 }

2 个答案:

答案 0 :(得分:11)

这似乎很容易。使用enumerateIndexesUsingBlock:枚举索引集并将每个索引粘贴到NSIndexPath对象中:

NSMutableArray * paths = [NSMutableArray array];
[indexes enumerateIndexesUsingBlock:^(NSUInteger index, BOOL *stop) {
        [paths addObject:[NSIndexPath indexPathWithIndex:index]];
    }];
[self.tableView insertRowsAtIndexPaths:paths
                      withRowAnimation:<#(UITableViewRowAnimation)#>];

如果你的表视图有部分,它只是有点复杂,因为你需要获得正确的部分编号,并在索引路径中指定它:

NSUInteger sectionAndRow[2] = {sectionNumber, index};
[NSIndexPath indexPathWithIndexes:sectionAndRow
                           length:2];

答案 1 :(得分:1)

这是NSIndexSet的一个类别:

@interface NSIndexSet (mxcl)
- (NSArray *)indexPaths;
@end

@implementation NSIndexSet (mxcl)

- (NSArray *)indexPaths {
    NSUInteger rows[self.count];
    [self getIndexes:rows maxCount:self.count inIndexRange:NULL];
    NSIndexPath *paths[self.count];
    for (int x = 0; x < self.count; ++x)
        paths[x] = [NSIndexPath indexPathForRow:rows[x] inSection:0];
    return [NSArray arrayWithObjects:paths count:self.count];
}

@end

使用NSMutableArray时代码会更短,但是当我想要使结果保持不变时,我会试图阻止制作可变对象。