Take the 2-minute tour ×

I have been struggling with this question for couple days now. Really need your help and opinion.

We have a string, that holds a text:

NSString *contentOfFile = [[NSString alloc] initWithString:@"This is string#1"];

Now I have to log symbols, that were met in this string without duplicates. Result should look like this:

whitespace symbol here

I know that this is solved very simple in C code using char set and iterators but I am looking for the same simple and elegant way of handling this operation in objective-c.

I was thinking of using NSCharacterSet on the string somehow but I have a lack of knowledge in objective-c so I need your help guys please. Thanks in advance to everyone who replies.

share|improve this question
A lack of knowledge in <insert language here> does not mean that you can't read the documentation for <library in that language>. Hint. –  user529758 Dec 14 '13 at 22:25
Thanks for the hint! –  Soberman Dec 14 '13 at 22:27
That link points to the documentation of the addCharactersInString: method of NSMutableCharacterSet. With that, your problem can be solved in one LOC. –  user529758 Dec 14 '13 at 22:28
Any hint on how to print characterset please? –  Soberman Dec 14 '13 at 22:57
Good suggestion. How would you then get every character out of it? Loop through the entire unicode character set and call characterIsMember for every one? –  Duncan C Dec 15 '13 at 0:40

2 Answers 2

up vote 0 down vote accepted

Take advantage of a trait of NSSet: Its members are distinct.

NSString *contentOfFile = @"This is string#1";

NSMutableSet *set = [NSMutableSet set];

NSUInteger length = [contentOfFile length];
for (NSUInteger index = 0; index < length; index++)
    NSString *substring = [contentOfFile substringWithRange:NSMakeRange(index, 1)];
    [set addObject:substring];

NSLog(@"%@", set);

However, there's one remaining problem, and that is the members of a set are also unordered. Fortunately, arrays are ordered. So if you change the last line:

NSSortDescriptor *sortDescriptor = [NSSortDescriptor sortDescriptorWithKey:@"self" ascending:YES];
NSArray *array = [set sortedArrayUsingDescriptors:@[sortDescriptor]];

NSLog(@"%@", array);

If case insensitivity is important to you, there unfortunately is no 'case-insensitive' option for NSSet. However, you could convert your source string to all lowercase, like this:

NSString *contentOfFile = [@"This is string#1" lowercaseString];

and this would give you results exactly matching your sample output.

share|improve this answer
Thank you very much for your answer, it is exactly what I need. Way better than NSMutableCharacterSet as I had trouble printing it. Thank you again. –  Soberman Dec 15 '13 at 19:29
// Create the string

// Remove all whitespaces
NSString *whitespaceRemoval = [contentOfFile stringByReplacingOccurrencesOfString:@" " withString:@""];

// Initialize an array to store the characters
NSMutableArray *components = [NSMutableArray array];

// Iterate through the characters and add them to the array
for (int i = 0; i < [whitespaceRemoval length]; i++) {
    NSString *character = [NSString stringWithFormat:@"%c", [whitespaceRemoval characterAtIndex:i]];
    if (![components containsObject:character]) {
        [components addObject:character];
share|improve this answer
Thank you for the response. But in your example there will be occurrences of duplicate characters, while I have to get the characters only once, no duplicates –  Soberman Dec 15 '13 at 10:30
Then simply add a check to see if the array contains the object before adding it. See my updated answer. –  Jon Erickson Dec 15 '13 at 22:28

Your Answer


