How to check the last char of an NSString

If you're worried about performance, and you want to check for one character, using -characterAtIndex: method may well be faster. -hasSuffix: takes a string, so potentially needs to do more work than just checking a single character (though the difference may be trivial).

You can also use categories to add a method to NSString like this:

@interface NSString(StringUtilities)
    - (BOOL) endsWithCharacter: (unichar) c;
@end

@implementation NSString(StringUtilities)

    - (BOOL) endsWithCharacter: (unichar) c
    {
        NSUInteger length = [self length];
        return (length > 0) && ([self characterAtIndex: length - 1] == c);
    }

@end

// test it...
NSString *data = @"abcd,";
if ([data endsWithCharacter: L','])
{

}

You should profile, of course, to be sure. Bear in mind though that by putting endsWithCharacter into a method we've added the message passing overhead to it, which will skew the profiling results unless you do the same when profiling the alternatives.

All of this is probably premature optimisation for most cases - but of course if you're doing this test thousands of times a second it may well matter (in that case you would probably want to use the code directly in the loop, as message passing inside a tight inner loop isn't a great plan).


The NSString Programming Guide recommends:

If you simply want to determine whether a string contains a given pattern, you can use a predicate:

So, in your example:

NSString *data = @"abcde,";

// Create the predicate
NSPredicate *myPredicate = [NSPredicate predicateWithFormat:@"SELF endswith %@", @","];

// Run the predicate
// match == YES if the predicate is successful
BOOL match = [myPredicate evaluateWithObject:data];

// Do what you want
if (match) {
    // do something
}

A bit long winded to write? Maybe, but if you do this in more than one place it can be easily refactored into a helper method.

Here's a link to the NSPredicate docs.

Edit

I've done some profiling and it is overkill in this simple case (see my comment below). I'll leave the answer up here anyway just as an example of using predicates for this sort of thing.


NSString *data = @"abcde,";
if([data hasSuffix:@","]) // This returns true in this example
    // do something