How to capitalize the first word of the sentence in Objective-C?
Solution 1
Here is another go at it:
NSString *txt = @"hi my friends!";
txt = [txt stringByReplacingCharactersInRange:NSMakeRange(0,1) withString:[[txt substringToIndex:1] uppercaseString]];
For Swift language:
txt.replaceRange(txt.startIndex...txt.startIndex, with: String(txt[txt.startIndex]).capitalizedString)
Solution 2
The accepted answer is wrong. First, it is not correct to treat the units of NSString
as "characters" in the sense that a user expects. There are surrogate pairs. There are combining sequences. Splitting those will produce incorrect results. Second, it is not necessarily the case that uppercasing the first character produces the same result as capitalizing a word containing that character. Languages can be context-sensitive.
The correct way to do this is to get the frameworks to identify words (and possibly sentences) in the locale-appropriate manner. And also to capitalize in the locale-appropriate manner.
[aMutableString enumerateSubstringsInRange:NSMakeRange(0, [aMutableString length])
options:NSStringEnumerationByWords | NSStringEnumerationLocalized
usingBlock:^(NSString *substring, NSRange substringRange, NSRange enclosingRange, BOOL *stop) {
[aMutableString replaceCharactersInRange:substringRange
withString:[substring capitalizedStringWithLocale:[NSLocale currentLocale]]];
*stop = YES;
}];
It's possible that the first word of a string is not the same as the first word of the first sentence of a string. To identify the first (or each) sentence of the string and then capitalize the first word of that (or those), then surround the above in an outer invocation of -enumerateSubstringsInRange:options:usingBlock:
using NSStringEnumerationBySentences | NSStringEnumerationLocalized
. In the inner invocation, pass the substringRange
provided by the outer invocation as the range argument.
Solution 3
Use
- (NSArray *)componentsSeparatedByCharactersInSet:(NSCharacterSet *)separator
and capitalize the first object in the array and then use
- (NSString *)componentsJoinedByString:(NSString *)separator
to join them back
Solution 4
pString = [pString
stringByReplacingCharactersInRange:NSMakeRange(0,1)
withString:[[pString substringToIndex:1] capitalizedString]];
Solution 5
An alternative solution in Swift:
var str = "hello"
if count(str) > 0 {
str.splice(String(str.removeAtIndex(str.startIndex)).uppercaseString, atIndex: str.startIndex)
}
wal
Updated on September 09, 2020Comments
-
wal over 3 years
I've already found how to capitalize all words of the sentence, but not the first word only.
NSString *txt =@"hi my friends!" [txt capitalizedString];
I don't want to change to lower case and capitalize the first char. I'd like to capitalize the first word only without change the others.
-
Teja Kantamneni about 14 yearsI am pretty alien to Objective-c, but you have to do so much to just capitalize the word??
-
Tuomas Pelkonen about 14 yearsYes, to capitalize the first word only. Unfortunately, Objective-C is not like Python where every operation can be done on one line.
-
Chuck about 14 years@Teja: NSString does not natively support doing something to just one "word" in a string, and it's quite a verbose language anyway, so yes.
-
Johan Kool about 14 yearsJust make sure that the string is always at least 1 character long, or that you are ready to handle the exception thrown when that's not the case.
-
looneydoodle almost 12 yearsAdd a if([txt length] > 1) check before you replace the string with the capitalized string.
-
Johan Kool almost 12 years@looneydoodle You mean
if ([txt length] > 0)
. It works fine if the length is 1. -
John Erck over 10 yearsSuggested edit: Add semi-colon as last character of first line. Would avert Xcode error on copy paste.
-
Ken Thomases almost 10 yearsThis answer is wrong. See my answer for the correct approach.
-
Authman Apatira about 9 yearsFor those who'd like to capitalize the first letter of every word, just change the last line to read
*stop = enclosingRange.location + enclosingRange.length == self.length;
-
Ken Thomases about 9 yearsIf you want to capitalize every word, then there's no need to enumerate by words at all. That's the default behavior of
-capitalizedStringWithLocale:
. Even if you did want to enumerate every word, the way to do that is to simply never set*stop
. The enumeration will naturally end at the end of the string. (In general in Cocoa's enumeration-with-block methods, you should never set*stop
unless you're setting it to true. That's mostly important in concurrent enumerations, but it's in the design contract for all cases.) -
Johan Kool almost 9 yearsSee my other answer for a Swift solution to the problem of capitalizing the first character in a string. Ken Thomases has a point that you need to take localisation in account, and I recommend his answer is that is what you need, but in many cases this approach is sufficient.
-
keithbhunter over 7 yearsFor languages where every noun is capitalized, like German, this will not work. It will only capitalize the first word in the sentence instead of every noun.
-
Ken Thomases over 7 years@keithbhunter, OK, but that's not what the question was about. And I'd be surprised if there were any API which did the right thing for the situation you posit.
-
Arpit B Parekh about 4 yearsWhat is splice ?
-
Johan Kool about 4 years@ArpitBParekh This code is old. It worked in Swift at the time I posted it, but
splice
as been replaced since. -
Arpit B Parekh about 4 yearsThnak you for the answer @Johan Kool