Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to compare two NSArrays for equal content?

I have two NSArrays where the objects of the arrays are the same but might be in different indices. It should print both are equal irrespective of their indices.

NSArray *arr1 = [[NSArray alloc]initWithObjects:@"aa", @"bb", @"1", @"cc", nil];
NSArray *arr2 = [[NSArray alloc]initWithObjects:@"bb", @"cc", @"1", @"aa", nil];

if ([arr1 isEqualToArray:arr2])
{
    NSLog(@"Equal");
}
else
{
    NSLog(@"Not equal");
}

The above code is printing 'Not equal' but it should print 'Equal'. How can I do this?

like image 779
Ravi Avatar asked Dec 11 '12 06:12

Ravi


2 Answers

Those two arrays are not equal. Two arrays are equal is they both have the same objects in the same order.

If you want to compare with no regard to order then you need to use two NSSet objects.

NSSet *set1 = [NSSet setWithArray:arr1];
NSSet *set2 = [NSSet setWithArray:arr2];

if ([set1 isEqualToSet:set2]) {
    // equal
}
like image 100
rmaddy Avatar answered Oct 10 '22 22:10

rmaddy


Most of the answers here actually do not work for fairly common cases (see their comments). There is a very good data structure that will solve this problem: NSCountedSet.

The counted set is unordered, but does care about the number of items present, so you don't end up with @[1, @1, @2] == @[@1, @2, @2].

NSArray *array1 = @[@1, @1, @2];
NSArray *array2 = @[@1, @2, @2];

NSCountedSet *set1 = [[NSCountedSet alloc] initWithArray:array1];
NSCountedSet *set2 = [[NSCountedSet alloc] initWithArray:array2];

BOOL isEqual = [set1 isEqualToSet:set2];
NSLog(@"isEqual:%d", isEqual);
like image 42
OC Rickard Avatar answered Oct 10 '22 21:10

OC Rickard