@[ @"Peter", @"Paul", @"Mary", @"Joe", @"Jane", @"Alice", @"Bob" ]
どのように私は最も簡単にこの平坦化された配列を作成することができますか?
@[ @"Peter", @"Paul", @"Mary", @"Joe", @"Jane", @"Alice", @"Bob" ]
どのように私は最も簡単にこの平坦化された配列を作成することができますか?
キー値コーディング(KVC)コレクション演算子@unionOfArrays
は、1レベルの配列を平坦化するため、2回適用することで目的の結果が得られます。
コレクション演算子(@count
以外)には、コレクションプロパティへのキーパスが必要です。オブジェクトは既に配列(したがってコレクション)であるため、キーパスはself
でなければなりません。
NSArray *flattenedArray = [threeDimensionalArray valueForKeyPath: @"@[email protected]"];
私はこのスレッドが少し古いですが実現するが、私は解決策が必要:私たちは、そのための3D配列を平らにするために、次のKVCの呼び出しを得self
キーパスで二回@unionOfArrays
を適用する必要が
深いレベルの数は本当に重要ではありません。次のメソッドをNSArrayのカテゴリに追加することができます。私も、これらのメソッドのテスト含まれている:
// This is the method that would be used from an outside class
- (NSArray *)flatten {
NSArray *array = self;
while (![array isFlattened]) {
array = [array flattenOneLevel];
}
return [NSArray arrayWithArray:array];
}
- (NSArray *)flattenOneLevel {
NSMutableArray *array = [NSMutableArray array];
for (id object in self) {
[object isKindOfClass:self.class] ? [array addObjectsFromArray:object] : [array addObject:object];
}
return array;
}
- (BOOL)isFlattened {
BOOL flattened = YES;
for (id object in self) {
if ([object isKindOfClass:self.class]) {
flattened = NO;
break;
}
}
return flattened;
}
ここにそれが正常に機能するように、これらのメソッドのテストです:
it(@"should flatten an array", ^{
NSArray *initialArray = @[@[@23, @354, @1, @[@7], @[@[@3]]], @[@[@890], @2, @[@[@6], @8]]];
NSArray *expectedArray = @[@23, @354, @1, @7, @3, @890, @2, @6, @8];
expect([initialArray flatten]).equal(expectedArray);
});
(上のより多くのメモリを取る再帰を使用して、代替の答えを、スタック)が、再帰を好きな人のために、読むために簡単です:
- (NSArray *) flatten;
{
NSMutableArray *flattedArray = [NSMutableArray new];
for (id item in self) {
if ([[item class] isSubclassOfClass:[NSArray class]]) {
[flattedArray addObjectsFromArray:[item flatten]];
} else {
[flattedArray addObject:item];
}
}
return flattedArray;
}
とテストの拡張:
を+ (void) unitTests;
{
NSArray *flattenedArray;
NSArray *initialArray1 = @[@[@23, @354, @1, @[@7], @[@[@3]]], @[@[@890], @2, @[@[@6], @8]]];
NSArray *expectedArray1 = @[@23, @354, @1, @7, @3, @890, @2, @6, @8];
flattenedArray = [initialArray1 flatten];
SPASLogDetail(@"flattenedArray: %@", flattenedArray);
AssertIf(![flattenedArray isEqualToArray:expectedArray1], @"Arrays are not equal");
NSArray *initialArray2 = @[@[@23, @354, @1, [@[@7] mutableCopy], @[@[@3]]], @[[@[@890] mutableCopy], @2, @[@[@6], @8]]];
NSArray *expectedArray2 = expectedArray1;
flattenedArray = [initialArray2 flatten];
SPASLogDetail(@"flattenedArray: %@", flattenedArray);
AssertIf(![flattenedArray isEqualToArray:expectedArray2], @"Arrays are not equal");
}
質問と回答の両方に+1、優雅な解決策。 –