IT

Objective-C에서 NSArray를 새로운 NSArray로 필터링

lottoking 2020. 7. 18. 09:42
반응형

Objective-C에서 NSArray를 새로운 NSArray로 필터링


나는 가지고있는 특정 기준을 배열에서 NSArray새로운 것을 생성합니다 NSArray. 기준은 반환하는 함수에 의해 결정 BOOL됩니다.

I는 생성 할 NSMutableArray소스 어레이를 통해 반복, 및 상기 필터 함수를 받아들이고 다음의 불변 버전을 생성하는 개체를 통해 복사합니다.

더 좋은 방법이 있습니까?


NSArrayNSMutableArray필터 어레이 목차 방법을 제공한다. 지정된 술어와 일치하는 수신자의 오브젝트 를 포함하는 새 배열을 리턴하는 filtersArrayUsingPredicate :NSArray제공합니다 . filterUsingPredicate : 하여 지정된 술어에 대해 관련 컨텐츠의 컨텐츠를 평가하고 일치하는 오브젝트 추가 합니다. 단지 방법은 다음 예에 설명되어 있습니다.NSMutableArray

NSMutableArray *array =
    [NSMutableArray arrayWithObjects:@"Bill", @"Ben", @"Chris", @"Melissa", nil];

NSPredicate *bPredicate =
    [NSPredicate predicateWithFormat:@"SELF beginswith[c] 'b'"];
NSArray *beginWithB =
    [array filteredArrayUsingPredicate:bPredicate];
// beginWithB contains { @"Bill", @"Ben" }.

NSPredicate *sPredicate =
    [NSPredicate predicateWithFormat:@"SELF contains[c] 's'"];
[array filteredArrayUsingPredicate:sPredicate];
// array now contains { @"Chris", @"Melissa" }

이 작업을 수행하는 방법은 다음을 사용하는 것입니다 [NSPredicate predicateWithBlock:].

NSArray *filteredArray = [array filteredArrayUsingPredicate:[NSPredicate predicateWithBlock:^BOOL(id object, NSDictionary *bindings) {
    return [object shouldIKeepYou];  // Return YES for each object you want in filteredArray.
}]];

나는 그것이 간결하다고 생각합니다.


빠른 :

NSArraySwift에서 s로 작업하는 사람들에게는 이보다 간결한 버전을 선호 할 수 있습니다 .

nsArray = nsArray.filter { $0.shouldIKeepYou() }

filter에 대한 메소드 일뿐입니다 Array( NSArray암시 적으로 Swift 's에 연결됨 Array). 배열에서 하나의 객체를 가져와 반환하는 클로저라는 하나의 인수가 필요합니다 Bool. 클로저 true에서 필터링 된 배열에 원하는 객체를 반환 합니다.


OS X 10.6 / iOS 4.0 이상인 경우 NSPredicate보다 블록을 사용하는 것이 좋습니다. 참조 또는 추가 자신의 범주를 쓰기 또는 추가 방법 ( ).-[NSArray indexesOfObjectsPassingTest:]-select:-filter:

다른 사람이 해당 카테고리를 작성하고 테스트하는 등의 작업을 원하십니까? BlocksKit ( array docs )을 확인하십시오 . 거기에 그리고 많은 예를 들어 검색 말하자면 찾을 수 더 많은 예제, "있는 NSArray를 블록 카테고리 선택이" .


Clay Bridges의 답변을 기반으로 다음은 블록을 사용하여 필터링하는 예제입니다 ( yourArray배열 변수 이름 및 testFunc테스트 이름 함수 변경 ).

yourArray = [yourArray objectsAtIndexes:[yourArray indexesOfObjectsPassingTest:^BOOL(id obj, NSUInteger idx, BOOL *stop) {
    return [self testFunc:obj];
}]];

클래스가 모두 포함이라고 가정하면 기준에 사용하는 함수를 호출하는 기본 클래스의 범주로 메소드를 추가 할 수 있습니다. 그런 다음 메소드 메소드를 참조하는 NSPredicate를 만듭니다.

일부 카테고리에서는 함수를 사용하는 메소드를 정의하십시오.

@implementation BaseClass (SomeCategory)
- (BOOL)myMethod {
    return someComparisonFunction(self, whatever);
}
@end

그런 다음 필터링 할 위치 :

- (NSArray *)myFilteredObjects {
    NSPredicate *pred = [NSPredicate predicateWithFormat:@"myMethod = TRUE"];
    return [myArray filteredArrayUsingPredicate:pred];
}

물론 함수가 클래스 내에서 접근 가능한 속성과 만 비교하는 경우 함수 조건을 조건으로 변환하는 것이 더 쉬울 수 있습니다.


NSPredicate필터에 컬렉션을 조건을 구성하는 넥스트 스텝의 방법이다 ( NSArray, NSSet, NSDictionary).

예를 들어 두 개의 배열 arrfilteredarr다음을 고려하십시오 .

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"SELF contains[c] %@",@"c"];

filteredarr = [NSMutableArray arrayWithArray:[arr filteredArrayUsingPredicate:predicate]];

filterarr에는 문자 c 만 포함하는 항목이 확실히 있습니다.

SQL 배경이 적은 사람들을 쉽게 기억할 수 있도록

*--select * from tbl where column1 like '%a%'--*

1) tbl에서 * 선택 -> 컬렉션

2) '% a %'와 같은 열 1- >NSPredicate *predicate = [NSPredicate predicateWithFormat:@"SELF contains[c] %@",@"c"];

3) select * from tbl where column1 like '% a %' ->

[NSMutableArray arrayWithArray:[arr filteredArrayUsingPredicate:predicate]];

이게 도움이 되길 바란다


NSArray + Xh

@interface NSArray (X)
/**
 *  @return new NSArray with objects, that passing test block
 */
- (NSArray *)filteredArrayPassingTest:(BOOL (^)(id obj, NSUInteger idx, BOOL *stop))predicate;
@end

NSArray + Xm

@implementation NSArray (X)

- (NSArray *)filteredArrayPassingTest:(BOOL (^)(id obj, NSUInteger idx, BOOL *stop))predicate
{
    return [self objectsAtIndexes:[self indexesOfObjectsPassingTest:predicate]];
}

@end

여기에서이 카테고리를 다운로드 할 수 있습니다.


이 라이브러리 체크 아웃

https://github.com/BadChoice/Collection

루프를 다시 작성하지 않는 쉬운 배열 함수가 많이 있습니다.

따라서 다음을 수행 할 수 있습니다.

NSArray* youngHeroes = [self.heroes filter:^BOOL(Hero *object) {
    return object.age.intValue < 20;
}];

또는

NSArray* oldHeroes = [self.heroes reject:^BOOL(Hero *object) {
    return object.age.intValue < 20;
}];

가장 좋고 쉬운 방법은이 방법을 만들고 배열 및 값을 전달하는 것입니다.

- (NSArray *) filter:(NSArray *)array where:(NSString *)key is:(id)value{
    NSMutableArray *temArr=[[NSMutableArray alloc] init];
    for(NSDictionary *dic in self)
        if([dic[key] isEqual:value])
            [temArr addObject:dic];
    return temArr;
}

참고 URL : https://stackoverflow.com/questions/110332/filtering-nsarray-into-a-new-nsarray-in-objective-c

반응형