NSMutableArray的订单,桶排序和订单桶

时间:2012-03-09 07:30:07

标签: iphone objective-c nsmutablearray nsarray key-value

我有一个NSArray的{​​{1}}有一个有趣的Object,我想通过以下方式使用它:给定我带有属性的对象数组:

property; Object1 - Property A; Object2 - Property A; Object3 - Property B; Object4 - Property D; Object5 - Property D

我希望将这些属性按其属性排序到新数组中:

Object6 - Property D

Array1 - Objects Object1, Object2

Array2 - Objects Object3

然后在每个数组中,使用Array3 - Objects Object 4, Object5, Object6属性进行排序。

我试图通过创建字典来天真地实现这一点,通过像timeStamp这样的属性将有趣的对象添加到字典中。这种方法没有按预期工作,因为我最终需要使用if ([dictionary objectForKey:@"propertyVal"]) //add object else // create array for key, add object to array取消NSMutableDictionary,这是不可靠的。

我觉得这是一个相当普遍的问题,我很想听听我如何解决这个问题。代码很棒,但即使算法(使用适当的对象)也应该足够了。

1 个答案:

答案 0 :(得分:1)

这不是一个合适的存储桶排序,但应该适用于一组三个属性。有点摆弄,你应该能够针对任何数量的属性进行调整:

编辑。我制作了一个动态版本(只需根据需要设置属性类型):

- (NSMutableArray *)order:(NSDictionary *)objects byProperty:(id)property {
    NSMutableSet *propertySet = [NSMutableSet setWithCapacity:5]; // so we can count the unique properties
    for (Object *obj in [objects allValues]) {
        [propertySet addObject:[obj property]];
    }

    NSMutableArray *objectCollections = [NSMutableArray arrayWithCapacity:[propertySet count]];

    // create arrays for every property
    for (int i = 0; i < [objects allValues]; i++) {
        NSMutableArray *collection = [NSMutableArray arrayWithCapacity:5];
        [objectCollections addObject:collection];
    }  
    NSArray *allProperties = [propertySet allObjects];

    // push objects into arrays according to a certain property
    for (Object *obj in [dictionary allValues]) {
        [[objectCollections objectAtIndex:[allProperties indexOfObject:[obj property]] addObject:obj];
    }

    NSMutableArray *result = [NSMutableArray arrayWithCapacity:[objectCollections count]];
    // sort arrays by timestamp
    for (int i = 0; i < [objectCollections count]; i++) {
            [result addObject:[[objectCollections objectAtIndex:i] sortedArrayUsingComparator:^(id obj1, id obj2) {
            if ([(Object *)obj1 timeStamp] > [(Object *)obj2 timeStamp]) {
                return (NSComparisonResult)NSOrderedAscending;
            }
            if ([(Object *)obj1 timeStamp] < [(Object *)obj2 timeStamp]) {
                return (NSComparisonResult)NSOrderedDescending;
            }            
            return (NSComparisonResult)NSOrderedSame;
        }];
    }
    return result;
}