0

I am trying to check which array element's values are equal to each other or to the NSNumber 10. The array has count 15. The problem is that when I test the value against NSNumber 10 in an if statement, the code does not seem to evaluate.

In the array below, for example, the code should return that the value in index 0 is present in indices {0, 9, 10} since NSNumber 1 is present in index 0 and 10 and NSNumber 10 is present at index 9.

1-2-3-4-5-6-7-8-9-10-1-2-3-4-5

However, it only evaluates whether the NSNumber value in index 0 is equal to NSNumber 1 and not to NSNumber 10. The output is not as expected {0, 9, 10} but only {0, 10}.

for (NSNumber *number in mutableArray) {
    self.matchingIndex = [mutableArray indexesOfObjectsPassingTest:
                         ^BOOL(NSNumber *obj, NSUInteger idx, BOOL *stop) 
    {
        BOOL returnValue;
        NSNumber *ten = [NSNumber numberWithInt:10];
        if ([number isEqualToNumber:obj] || [number isEqualToNumber:ten])
        {
            returnValue = TRUE;
        }
        return returnValue;  
    }];
    [self testIndexSet:self.matchingIndex];
}     
SwiftArchitect
  • 47,376
  • 28
  • 140
  • 179
noobsmcgoobs
  • 2,716
  • 5
  • 32
  • 52
  • maybe the code you have pasted is not complete, but you only seem to be saving the very last result of the for loop, is this intentional? – Fonix Dec 30 '15 at 03:45
  • 1
    This isn't the cause of the problem, but `returnValue` is uninitialized when the `if` expression doesn't evaluate to true. – Ken Thomases Dec 30 '15 at 04:09
  • @Fonix Yeah, it's incomplete but basically I send `self.matchingIndex` as a parameter to another method before the fast enumeration closing bracket. But yes, you are correct, the code as is does that. Didn't include it because that part wasn't what was causing me issues. Will update for future viewers. – noobsmcgoobs Dec 30 '15 at 04:23
  • @KenThomases wouldn't it evaluate to FALSE? – noobsmcgoobs Dec 30 '15 at 04:28
  • 1
    Automatic (a.k.a. stack or local) variables are not initialized by default in C or Objective-C. The only exception is object pointers when using ARC. In the code you showed, `returnValue` has a random-ish junk value to start with. Assuming the `if` condition isn't true, it will remain that way because nothing ever sets it otherwise. – Ken Thomases Dec 30 '15 at 05:11
  • @KenThomases I see your point. Thanks. – noobsmcgoobs Dec 30 '15 at 10:08

1 Answers1

1

Your expectation is incorrect. number, the outer loop iterator will be equal to ten only for the @10 element in the array. The expected result for the loop is two indexes on the 1..5 elements, and one index for the rest.

If you'd like the loop to find the @10 element and include that with every result, change the condition from...

if ([number isEqualToNumber:obj] || [number isEqualToNumber:ten])

to...

if ([number isEqualToNumber:obj] || [obj isEqualToNumber:ten])

Incidentally, the block can be stated more simply as...

NSIndexSet *matchingIndex = [mutableArray indexesOfObjectsPassingTest:^BOOL(NSNumber *obj, NSUInteger idx, BOOL *stop) {
    return ([number isEqualToNumber:obj] || [obj isEqualToNumber:@10]);
}];
danh
  • 62,181
  • 10
  • 95
  • 136
  • Great, thanks. Just for curiosity, if the code needed to compare 2 non-identical arrays to find matching indexes, would the same code work? – noobsmcgoobs Dec 30 '15 at 04:40
  • Yes, but there's a better way. See here: http://stackoverflow.com/questions/6023548/finding-intersection-of-nsmutablearrays – danh Dec 30 '15 at 04:49