一个高效的条件筛选方法

2019-03-14  本文已影响0人  innepeace

背景:有一个元素为obj的数组,需要将其根据月份进行筛选,由每个月的数据组成数组,再将其作为元素组成一个数组。

eg:

原数组:@[

@{month:2018-12,num:10},

@{month:2018-10,num:9},

@{month:2018-11,num:5},

@{month:2018-12,num:8},

@{month:2018-11,num:9}

]

处理后的数组: @[

@[ @{month:2018-12,num:10}, @{month:2018-12,num:8}],

@[ @{month:2018-10,num:9}],

@[@{month:2018-11,num:5}, @{month:2018-11,num:9}]

]

难点:要在数组遍历的同时分组,并将其组成新的数组。否则若先便利确定小分组个数,就需要多次for循环。

解决办法:如难点所说,设计代码,使其遍历的同时组成新的数组,这样可以降低时间复杂度。代码如下:

/**

 将数据按月分组
 
 @param dataArr 源数据
 @return NSArray 处理后的数据
 */
- (NSArray *)sectionDataArrayWithArray:(NSArray *)dataArr {
    NSMutableArray *tempArr = [[NSMutableArray alloc] init];  // 处理后的数组
    // 先取所有的日期
    NSMutableArray *yyyyArr = [[NSMutableArray alloc] init];  // 数组内每个小分组
    [dataArr enumerateObjectsUsingBlock:^(RecordModel *obj, NSUInteger idx, BOOL * _Nonnull stop) {
        NSString *yyyymm = [NSDate dateStringWithString:obj.applydate inFormatString:DLDateFormatter_yyyyMMdd outFormatString:DLDateFormatter_yyyyMM];
        
        __block NSInteger index = -1;
        [yyyyArr enumerateObjectsUsingBlock:^(NSString *obj, NSUInteger idx, BOOL * _Nonnull stop) {
            if ([obj isEqualToString:yyyymm]) {
                index = idx;
                *stop = YES;
            }
        }]; // 判断 yyyyArr 是否包含了 yyyymm,若包含直接退出遍历,index = idx (即yyyymm在yyyyArr中的位置),不包含,完成遍历后 index 仍为 -1
        
        if (index != -1) { // 包含,在 yyyyArr 中加入 当前元素 yyyymm
            [tempArr[index] addObject:obj];
        } else { // 不包含,创建一个新的yyyyArr,将其加入 tempArr
            [yyyyArr addObject:yyyymm];
            [tempArr addObjectsFromArray:[@[obj] mutableCopy]];
        }
    }];
    
    return [tempArr copy];
}
上一篇 下一篇

猜你喜欢

热点阅读