PHP - Capitalise first character of each word expect certain words

做~自己de王妃 提交于 2019-12-11 00:31:56

问题


I have a batch of strings like so:

tHe iPad hAS gONE ouT of STOCK
PoWER uP YOur iPhone
wHAT moDEL is YOUR aPPLE iPHOne

I want to capitalise the first character of each word and have the remaining characters lowercase - except any references of iPhone or iPad. As in:

By using:

ucwords(strtolower($string));

This can do most of what is needed but obviously also does it on iPadand iPhone:

The Ipad Has Gone Out Of Stock
Power Up Your Iphone
What Model Is Your Apple Iphone

How can I do achieve the below:

The iPad Has Gone Out Of Stock
Power Up Your iPhone
What Model Is Your Apple iPhone

回答1:


You can use str_replace for this. If you use arrays for the first two arguments, you can define a set of words and replacements:

echo str_replace(['Ipad', 'Iphone'], ['iPad', 'iPhone'], ucwords(strtolower($string)));

From the documentation:

If search and replace are arrays, then str_replace() takes a value from each array and uses them to search and replace on subject.




回答2:


As you know the specific words, and they are limited, why don't you just revert them back after the total capitalization, just as following

$string = ucwords(strtolower($string));
$string = str_replace("Ipad","iPad", $string);
$string = str_replace ("Iphone","iPhone", $string);



回答3:


+1 forA more generic solution:

<?php

$text = <<<END_TEXT
PoWER uP YOur iPhone
tHe iPad hAS gONE ouT of STOCK 
wHAT moDEL is YOUR aPPLE iPHOne
END_TEXT;

$text = preg_replace(array('/iphone/i', '/iPad/i'), array('iPhone', 'iPad'), $text);
$text = preg_replace_callback('/(\b(?!iPad|iPhone)[a-zA-Z0-9]+)/', 
     function ($match) { return ucfirst(strtolower($match[1])); }, $text);

echo $text;

Demo

Uses a negative lookahead in the regex to exclude the listed words from matching and manipulates the others via a callback to an anonymous function. That way, you can do any kind of manipulation, for example reversing the string etc.

+1 for the other answers, as they are perfect for this special task.




回答4:


Instead of having to write the lower- and uppercase version of each word you want to exclude respectively and thus having to write them twice, you could only define them once in an array and using str_ireplace instead of str_replace like this:

$string = "tHe IPHONE and iPad hAS gONE ouT of STOCK";

$excludedWords = array(
    "iPad",
    "iPhone"
);

echo str_ireplace($excludedWords, $excludedWords, ucwords(strtolower($string)));

Which would result in

The iPhone And iPad Has Gone Out Of Stock

This would then replace all occurrences of these words with the version you've defined in the array.

Edit:

Keep in mind that using this, words like "shipadvertise" would be replaced with "shiPadvertise". If you want to prevent this, you could use a more advanced solution using regular expressions:

$string = "tHe IPHONE and shipadvertise iPad hAS gONE ouT of STOCK";

$excludedWords = array(
    "iPad",
    "iPhone"
);
$excludedWordsReg = array_map(function($a) { return '/(?<=[\s\t\r\n\f\v])'.preg_quote($a).'/i'; }, $excludedWords);

echo preg_replace($excludedWordsReg, $excludedWords, ucwords(strtolower($string)));

This would then correctly resolve into

The iPhone And Shipadvertise iPad Has Gone Out Of Stock

I've used the delimiters for determining words ucwords uses by default.




回答5:


Best practice is to call strtolower() on the input string straight away (syck's answer doesn't do this).

I'll offer a pure regex solution that will appropriately target your ipad and iphone words and capitalize their seconds letter while capitalizing the first letter of all other words.

Code: (PHP Demo) (Pattern Demo)

$strings = [
    "tHe iPad hAS gONE ouT of STOCK
PoWER uP YOur iPhone
wHAT moDEL is YOUR aPPLE iPHOne",           // OP's input string
    "fly the chopper to the helipad.
an audiphone is a type of hearing aid
consisting of a diaphragm that, when
placed against the upper teeth, conveys
sound vibrations to the inner ear"          // some gotcha strings in this element
];

foreach ($strings as $string) {
    echo preg_replace_callback('~\bi\K(?:pad|phone)\b|[a-z]+~', function($m) {return ucfirst($m[0]);}, strtolower($string));
    echo "\n---\n";
}

Output:

The iPad Has Gone Out Of Stock
Power Up Your iPhone
What Model Is Your Apple iPhone
---
Fly The Chopper To The Helipad.
An Audiphone Is A Type Of Hearing Aid
Consisting Of A Diaphragm That, When
Placed Against The Upper Teeth, Conveys
Sound Vibrations To The Inner Ear
---

Probably the only parts to mention about the regex pattern is that \K means "restart the fullstring match" or in other words "consume and forget the previous character(s) in the current match".



来源:https://stackoverflow.com/questions/34318062/php-capitalise-first-character-of-each-word-expect-certain-words

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!