Skip to content

Instantly share code, notes, and snippets.

@conradev
Created August 15, 2012 19:00
Show Gist options
  • Save conradev/3362607 to your computer and use it in GitHub Desktop.
Save conradev/3362607 to your computer and use it in GitHub Desktop.
Recursively remove NSNull instances
// Use case being removing null values from the results of JSON encoding (thus only supports dictionaries and arrays)
__block id (^removeNull)(id) = ^(id rootObject) {
// Recurse through dictionaries
if ([rootObject isKindOfClass:[NSDictionary class]]) {
NSMutableDictionary *sanitizedDictionary = [NSMutableDictionary dictionaryWithDictionary:rootObject];
[rootObject enumerateKeysAndObjectsUsingBlock:^(id key, id obj, BOOL *stop) {
id sanitized = removeNull(obj);
if (!sanitized) {
[sanitizedDictionary removeObjectForKey:key];
} else {
[sanitizedDictionary setObject:sanitized forKey:key];
}
}];
return [NSDictionary dictionaryWithDictionary:sanitizedDictionary];
}
// Recurse through arrays
if ([rootObject isKindOfClass:[NSArray class]]) {
NSMutableArray *sanitizedArray = [NSMutableArray arrayWithArray:rootObject];
[rootObject enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
id sanitized = removeNull(obj);
if (!sanitized) {
[sanitizedArray removeObjectIdenticalTo:obj];
} else {
[sanitizedArray replaceObjectAtIndex:[sanitizedArray indexOfObject:obj] withObject:sanitized];
}
}];
return [NSArray arrayWithArray:sanitizedArray];
}
// Base case
if ([rootObject isKindOfClass:[NSNull class]]) {
return (id)nil;
} else {
return rootObject;
}
};
@wxactly
Copy link

wxactly commented Jan 28, 2013

Xcode warning on line 7:

Capturing 'removeNull' strongly in this block is likely to lead to a retain cycle

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment