Objective-C - 删除带有自定义子对象的重复项
Objective-C - Removing duplicates with custom sub-objects
我有一个弹出式列表,其中列出了出境和入境机场代码,如下所示:
Leg -- JFK DXB
Leg -- JFK DXB
Leg -- LS14 CFR
Leg -- LS14 EGSG
Leg -- OXF CFR
Leg -- OXF CFR
Leg -- JFK DXB
Leg -- DXB OXF
Leg -- DXB JFK
Leg -- CFR GVA
Leg -- JFK TDX
Leg -- JFK DXB
Leg -- TDX DXB
Leg -- GVA OXF
我想删除出发和到达匹配的所有重复项(即:JFK - DXB)
机场代码是自定义子代码或第三方对象,因此它不像进行字符串比较那么简单。
在下文中,我正在循环以摆脱任何 nil 对象
NSArray *charters = [CharterRequest charterRequestsForUser:[User currentUser] inContext:[NSManagedObjectContext mainContext]];
NSMutableArray *charterReq = [NSMutableArray array];
for (CharterRequest *request in charters)
{
CharterRequestLeg *leg = [request initialLeg];
if ( (leg.departureAirport.code != nil) && (leg.destinationAirport.code != nil) ) {
[charterReq addObject:request];
}
}
最终我会在航站楼输出机场代码
// someIndex could be any index, but lets say its 1 for now
VICCharterRequest *request = charterReq[someIndex];
VICCharterRequestLeg *leg = [request initialLeg];
NSString *returnedString = [NSString stringWithFormat:@"%@ - %@", leg.departureAirport.code, leg.destinationAirport.code];
NSLog(@"Leg = %@", returnedString);
我遇到的问题是我得到了很多重复的 destination/arrival 机场,例如 JFK DXB 会出现多次。
是否有合理的方法来去除所有重复项,留下唯一性?
非常感谢
目前我有这个代码,它总是 returns 50。由于重复,它应该比这个少得多;
// Filter out nils
for (VICCharterRequest *request in charters)
{
VICCharterRequestLeg *leg = [request initialLeg];
if ( (leg.departureAirport.code != nil) && (leg.destinationAirport.code != nil) ) {
[list addObject:request];
}
}
NSMutableSet *seenItems = [NSMutableSet set];
NSPredicate *dupPred = [NSPredicate predicateWithBlock: ^BOOL(id obj, NSDictionary *bind) {
VICCharterRequestLeg *leg = [obj initialLeg];
BOOL seen = ([seenItems containsObject:leg.departureAirport] && [seenItems containsObject:leg.destinationAirport]);
//[seenItems containsObject:leg];
if (!seen) {
[seenItems addObject:obj];
}
return !seen;
}];
NSArray *filtered = [list filteredArrayUsingPredicate:dupPred];
NSLog(@"Filtered = %lu", filtered.count);
NSArray* array = ... // you can add your data to this array
NSMutableSet* existingset = [NSMutableSet set];
NSMutableArray* finalArray = [NSMutableArray array];
for (id object in array) {
if (![existingset containsObject:[object name]]) {
[existingset addObject:[object name]];
[finalArray addObject:object];
}
}
您需要设置一些类似的方法。
例如:
- (BOOL)isEqualToVICCharterRequest:(VICCharterRequest *)request {
if (!request) {
return NO;
}
BOOL depEqual = (!self.departureAirport.code && !request.departureAirport.code) || [self.departureAirport.code isEqualToString:request.departureAirport.code];
BOOL arrEqual = (!self.destinationAirport.code && !request.destinationAirport.code) || [self.birthday isEqualToDate:request.destinationAirport.code];
return depEqual && arrEqual;
}
那么你的循环代码将是:
for (CharterRequest *request in charters)
{
CharterRequestLeg *leg = [request initialLeg];
if ( ![request isEqualToVICCharterRequest:leg] ) {
[charterReq addObject:request];
}
}
如果您想更深入:
#pragma mark - NSObject
- (BOOL)isEqual:(id)object {
if (self == object) {
return YES;
}
if (![object isKindOfClass:[VICCharterRequest class]]) {
return NO;
}
return [self isEqualToVICCharterRequest:(isEqualToVICCharterRequest *)object];
}
- (NSUInteger)hash {
return [self.departureAirport.code hash] ^ [self.destinationAirport.code hash];
}
我有一个弹出式列表,其中列出了出境和入境机场代码,如下所示:
Leg -- JFK DXB
Leg -- JFK DXB
Leg -- LS14 CFR
Leg -- LS14 EGSG
Leg -- OXF CFR
Leg -- OXF CFR
Leg -- JFK DXB
Leg -- DXB OXF
Leg -- DXB JFK
Leg -- CFR GVA
Leg -- JFK TDX
Leg -- JFK DXB
Leg -- TDX DXB
Leg -- GVA OXF
我想删除出发和到达匹配的所有重复项(即:JFK - DXB)
机场代码是自定义子代码或第三方对象,因此它不像进行字符串比较那么简单。
在下文中,我正在循环以摆脱任何 nil 对象
NSArray *charters = [CharterRequest charterRequestsForUser:[User currentUser] inContext:[NSManagedObjectContext mainContext]];
NSMutableArray *charterReq = [NSMutableArray array];
for (CharterRequest *request in charters)
{
CharterRequestLeg *leg = [request initialLeg];
if ( (leg.departureAirport.code != nil) && (leg.destinationAirport.code != nil) ) {
[charterReq addObject:request];
}
}
最终我会在航站楼输出机场代码
// someIndex could be any index, but lets say its 1 for now
VICCharterRequest *request = charterReq[someIndex];
VICCharterRequestLeg *leg = [request initialLeg];
NSString *returnedString = [NSString stringWithFormat:@"%@ - %@", leg.departureAirport.code, leg.destinationAirport.code];
NSLog(@"Leg = %@", returnedString);
我遇到的问题是我得到了很多重复的 destination/arrival 机场,例如 JFK DXB 会出现多次。
是否有合理的方法来去除所有重复项,留下唯一性?
非常感谢
目前我有这个代码,它总是 returns 50。由于重复,它应该比这个少得多;
// Filter out nils
for (VICCharterRequest *request in charters)
{
VICCharterRequestLeg *leg = [request initialLeg];
if ( (leg.departureAirport.code != nil) && (leg.destinationAirport.code != nil) ) {
[list addObject:request];
}
}
NSMutableSet *seenItems = [NSMutableSet set];
NSPredicate *dupPred = [NSPredicate predicateWithBlock: ^BOOL(id obj, NSDictionary *bind) {
VICCharterRequestLeg *leg = [obj initialLeg];
BOOL seen = ([seenItems containsObject:leg.departureAirport] && [seenItems containsObject:leg.destinationAirport]);
//[seenItems containsObject:leg];
if (!seen) {
[seenItems addObject:obj];
}
return !seen;
}];
NSArray *filtered = [list filteredArrayUsingPredicate:dupPred];
NSLog(@"Filtered = %lu", filtered.count);
NSArray* array = ... // you can add your data to this array
NSMutableSet* existingset = [NSMutableSet set];
NSMutableArray* finalArray = [NSMutableArray array];
for (id object in array) {
if (![existingset containsObject:[object name]]) {
[existingset addObject:[object name]];
[finalArray addObject:object];
}
}
您需要设置一些类似的方法。
例如:
- (BOOL)isEqualToVICCharterRequest:(VICCharterRequest *)request {
if (!request) {
return NO;
}
BOOL depEqual = (!self.departureAirport.code && !request.departureAirport.code) || [self.departureAirport.code isEqualToString:request.departureAirport.code];
BOOL arrEqual = (!self.destinationAirport.code && !request.destinationAirport.code) || [self.birthday isEqualToDate:request.destinationAirport.code];
return depEqual && arrEqual;
}
那么你的循环代码将是:
for (CharterRequest *request in charters)
{
CharterRequestLeg *leg = [request initialLeg];
if ( ![request isEqualToVICCharterRequest:leg] ) {
[charterReq addObject:request];
}
}
如果您想更深入:
#pragma mark - NSObject
- (BOOL)isEqual:(id)object {
if (self == object) {
return YES;
}
if (![object isKindOfClass:[VICCharterRequest class]]) {
return NO;
}
return [self isEqualToVICCharterRequest:(isEqualToVICCharterRequest *)object];
}
- (NSUInteger)hash {
return [self.departureAirport.code hash] ^ [self.destinationAirport.code hash];
}