"The Ministry Of Truth" challenge at CodeEval.com

I am working on another challenge from CodeEval.com and this is a bit harder. I would like to get some feedback on my logic of solving the challenge. Also there is probably one edge case that I missed because when I submit it to CodeEval I get different results. Once I received 95% correct and another time 100%.

The Ministry of Truth

It's 1984, and you are working as an official at the Ministry of Truth. You have intersected a message subjected to Big Brother's doctrine.

Your task is to delete letters from certain "utterances" in order to replace them with an "utterance" approved by the Ministry.

A "word" is a single sequence of Latin letters, and an "utterance" is a sequence of multiple words and spaces.

To compare two "utterances," you have to replace all blocks of spaces with one space. Utterances are considered to be identical when resulting expressions match.

One line contains two different expressions separated by semicolon ';'. The first expression is the original utterance, and the second one is the utterance you want to get.

If you cannot fulfill the order, print a single line «I cannot fix history». Otherwise, output the original utterance by replacing the letters that must be erased with underscore and by replacing all blocks of white spaces with a single white space.

Input Sample:

Higher meaning;Hi mean
this is impossible;im possible
twenty   two minutes;two minutes
Higher meaning;e


Output Sample:

Print the results, or "I cannot fix history" in case there is no match. E.g.:

Hi____ mean___
I cannot fix history
______ two minutes
____e_ _______


Here is my solution:

-(void)ministryOfTruth
{
NSString *line = @"ifcf hesaddasd  asdajds dsd f;";
NSArray *lineArray = [line componentsSeparatedByString:@";"]; //separate the original from approved
NSArray *originalUtteranceWithSpaces= [[lineArray objectAtIndex:0] componentsSeparatedByString:@" "]; //separate the words from spaces
NSMutableArray *originalUtterance  = [[NSMutableArray alloc]init];
for (NSString *word in originalUtteranceWithSpaces){
//get rid of the spaces
if (![word isEqual:@""]) {
}
}

NSArray *approvedUtterance = [[lineArray objectAtIndex:1] componentsSeparatedByString:@" "]; //separate the approved
NSMutableArray *resultArray = [[NSMutableArray alloc]init];
NSUInteger pos = 0;
BOOL isWordFound = NO;
if ([[approvedUtterance objectAtIndex:0] isEqual:@""]) {
isWordFound = NO;
}else{
for(NSString *approvedWord in approvedUtterance){
//itterate through the approved utterances
isWordFound = NO;
while (pos < [originalUtterance count]) {
//itterate through the words until you find the word that contains the approved word or goes through all the words
NSString *originalWord = [originalUtterance objectAtIndex:pos];

NSRange approvedWordLocation = [originalWord rangeOfString:approvedWord]; //check if the word contains approved word
if (approvedWordLocation.location !=NSNotFound) {
isWordFound = YES;
int letterPos = 0;
NSMutableString *tempOriginalWord = [originalWord mutableCopy];
//if approved word found then create a mutable copy of it and replace all chars in originalWord that are not the word with _
while (letterPos < [originalWord length]) {
if ((letterPos < approvedWordLocation.location) || (letterPos >= approvedWordLocation.location + approvedWordLocation.length)) {
//check if letterPos is before the found word or after
[tempOriginalWord replaceCharactersInRange:NSMakeRange(letterPos, 1) withString:@"_"];
}
letterPos+=1;
}
pos+=1; // move to the next original word
break; //get out of the while loop and check the next approved word
}else{
isWordFound = NO;
NSMutableString *tempOriginalWord = [originalWord mutableCopy];
for (int letterPos = 0; letterPos < [originalWord length]; letterPos++) {
[tempOriginalWord replaceCharactersInRange:NSMakeRange(letterPos, 1) withString:@"_"];
}
pos+=1; //move to the next original word
}

}
if (!isWordFound) {
//if approved word is not found then break out of the for loop and we are done.  I cannot fix history
break;
}

}
if (pos<[originalUtterance count] && isWordFound) {
//if all approved words are found and we still have word from origingal utterance then replace all charcters with _
NSMutableString *tempString = nil;
for (NSUInteger i = pos; i<[originalUtterance count]; i++) {
tempString = [[originalUtterance objectAtIndex:i] mutableCopy];
NSUInteger tempStringLength = [tempString length];
for (NSUInteger i = 0; i<tempStringLength; i++) {
[tempString replaceCharactersInRange:NSMakeRange(i,1) withString:[NSString stringWithFormat:@"_"]];
}
}
}

}
if (isWordFound) {
//Print results if all  approved words found
NSString *resultString = [resultArray componentsJoinedByString:@" "]; //create NSString from array and put space between the words
NSLog(@"resultArray %@",resultString);
}else{
NSLog(@"I cannot fix history");
}
}


Your code is nice, but could use a few improvements:

[array objectAtIndex:pos]


From what I can see, array[pos] is valid syntax for Objective-C, and is much better.

You're missing, in more than a few places, whitespace. For example:

• }else{ should be } else {,
• @"resultArray %@",resultString should have whitespace after the comma
• NSMakeRange(i,1) same as above: NSMakeRange(i, 1)
• i<tempStringLength: needs whitespace between the operator: i < tempStringLength
• pos+=1: same as above: pos += 1 (which could be pos++, right?)

You have two main for loops in your code, and in one, you use the data type int and in the other NSUInteger.
I would suggest keeping them the same, and also their names the same as one is letterPos and the other i.

for (int letterPos = 0
for (NSUInteger i = 0


You have quite a few empty lines that could be removed, also.

Other than that, your code looks nice.