Javascript Convert Names To Uppercase, Except Mc/mac/etc
Solution 1:
You can try something like this:
const input = "MacDonald";
const matches = input.match(/([A-Z][a-z]*)/g);
const output = matches.length > 1 ?
matches.reduce((acc, match, index) => {
if (index === 0) {
returnmatch;
}
return acc + match.toUpperCase();
}) :
input.toUpperCase();
First we take the input
apart by matching it against a simple regular expression. The match
method in the example will return ["Mac","Donald"]
.
Then, if there is only one match, we return it in uppercase.
In case of multiple matches, we construct the result by concatenating uppercase parts except for the first part.
Here's a version for a whole sentence:
const input = "Old MacDonald is a fine man.";
const output = input
.split(/\s/)
.map(word => {
const matches = word.match(/([A-Z][a-z]*)/g);
if (!matches || matches.length === 1) {
return word.toUpperCase();
}
return matches.reduce((acc, match, index) => {
return index === 0 ? match : acc + match.toUpperCase();
});
})
.join(' ');
// output == "OLD MacDONALD IS A FINE MAN."
Solution 2:
Sami Hult's answer covers most of the bases, but unfortunately refuses to work in After Effects due to syntax issues and map() and reduce() not being supported, and I wanted to make one small tweak, all-capsing only the last portion rather than all but the first (to account for a possible double prefix).
So based on that code, I came up with this:
functionstr_uppercase(str) {
str = str.split(/\s/);
var output = [];
for (i = 0; i < str.length; i++) {
var word = str[i];
var matches = word.match(/([A-Z][a-z]*)/g);
if (!matches || matches.length === 1) {
word = word.toUpperCase();
} else {
var x = matches.length - 1;
matches[x] = matches[x].toUpperCase();
word = matches.join('');
}
output.push(word);
}
return output.join(' ');
}
console.log(str_uppercase('Old MacMcDonald Had a farm'));
// => OLD MacMcDONALD HAD A FARM
Solution 3:
The code below assumes a string prefix to be one capital letter character
followed by one or more small letter characters
followed by one capital letter character
and always at the beginning of the whole word.
The prefix will be retained as it is and the rest will be capitalized.
const input = [
"McDonald",
"MacDonald",
"Mcdonald",
"mcDonald",
"mcdonald"
];
// Function for converting to special uppercaseconst specialUpperCase = function(item) {
// Find prefix (one or more lower case characters between upper case character - at the beginning)const match = item.match(/^[A-Z][a-z]+[A-Z]/);
if (match) {
// If prefix, capitalize only the remainingreturn match[0] + item.substr(match[0].length).toLocaleUpperCase();
}
// If no prefix, capitalize the whole stringreturn item.toLocaleUpperCase();
};
const output = input.map(specialUpperCase);
console.log(output);
Solution 4:
The easiest solution would probably be to keep a list of prefixes and test if the word starts with one of these:
//Prefixes to look forvar prefixToKeep = [
"Mac",
"Mc"
];
//Selective uppercase functionfunctionselectiveUpperCase(text) {
//Find words by wordBoundariesreturn text.replace(/\b\w+\b/gim, function (word) {
//Test for prefixesfor (var prefixToKeepIndex = 0; prefixToKeepIndex < prefixToKeep.length; prefixToKeepIndex++) {
var prefix = prefixToKeep[prefixToKeepIndex];
if (word.indexOf(prefix) === 0) {
//prefix matches. Return prefix as is + rest of the word in uppercasereturn word.slice(0, prefix.length) + word.slice(prefix.length).toUpperCase();
}
}
//No prefix found, return word as uppercasereturn word.toUpperCase();
});
}
//TESTvar text = "Old MacDonald had a farm\nE-I-E-I-O\nAnd on this farm he had a cow\nE-I-E-I-O\nWith a moo-moo here\nAnd a moo-moo there\nHere a moo, there a moo\nEverywhere a moo-moo\nOld MacDonald had a farm\nE-I-E-I-O ";
console.log(selectiveUpperCase(text));
EDIT 1 - Upper-Lower-Upper Test
In response to the comments, this newer version tests for Upper-Lower-Upper cases and uses its findings to determine which parts to uppercase.
//Selective uppercase functionfunctionselectiveUpperCase(text) {
//Find words by wordBoundariesreturn text.replace(/\b\w+\b/gim, function (word) {
var reg = /[A-Z]+[a-z]+[A-Z]\w+/gm;
//Test for Upper-Lower-Upper comboif (reg.test(word) || reg.test(word)) {
//start at index 1var l = 0;
while (l++ < word.length) {
//move up the word and test for an uppercase letterif (word[l] === word[l].toUpperCase()) {
break;
}
l++;
//return the first slice (the prefix) as is and uppercase the restreturn word.slice(0, l) + word.slice(l).toUpperCase();
}
}
//No prefix found, return word as uppercasereturn word.toUpperCase();
});
}
//TESTvar text = "Old MacDonald had a farm\nE-I-E-I-O\nAnd on this farm he had a cow\nE-I-E-I-O\nWith a moo-moo here\nAnd a moo-moo there\nHere a moo, there a moo\nEverywhere a moo-moo\nOld McDonald had a farm\nE-I-E-I-O ";
console.log(selectiveUpperCase(text));
Solution 5:
ES6 version with RegEx, you can try below function replaceStr()
constreplaceStr = str => str.replace(/(^[A-Z])([a-z]{1,2})(.+)/,
(_, p1, p2, p3) => p1.toUpperCase() + p2 + p3.toUpperCase());
Post a Comment for "Javascript Convert Names To Uppercase, Except Mc/mac/etc"