Php 第一个字母大写在触摸和时失败

Php 第一个字母大写在触摸和时失败,php,Php,我有以下PHP函数,几乎在所有情况下都能正常工作: function NormalizeWords($str, $disallowAllUppercase = false){ $parts = explode(' ', $str); if($disallowAllUppercase){ $result = array_map(function($x){ return ucwords(strtolower($x)); },

我有以下PHP函数,几乎在所有情况下都能正常工作:

function NormalizeWords($str, $disallowAllUppercase = false){
    $parts = explode(' ', $str);

    if($disallowAllUppercase){
        $result = array_map(function($x){
            return ucwords(strtolower($x));
        }, $parts);
    }else{
        $result = array_map(function($x){
            if (!ctype_upper($x)) {
                return ucwords(strtolower($x));
            }
            return $x;
        }, $parts);
    }
    
    return implode(' ', $result);
}
但这里有一个例子,它没有抓住要点:

$testinput = "M&S ACME BUSINESS";
$testoutput = NormalizeWords($testinput);
die($testoutput);

Expected result: M&S ACME BUSINESS
Actual result: M&s ACME BUSINESS
s
变为小写

正如您所看到的,
$disallowlUppercase
仍然为false,因此任何大写字符都应该保留

以下是一些预期结果的示例:

"THIS IS MY BUSINESS NAME" ($disallowAllUppercase is true) - should be: "This Is My Business Name"
"THIS IS MY BUSINESS NAME" ($disallowAllUppercase is false) - should be: "THIS IS MY BUSINESS NAME"
"aNotheR BUSINESS nAME" ($disallowAllUppercase is true) - should be: "Another Business Name"
"aNotheR BUSINESS nAME" ($disallowAllUppercase is false) - should be: "Another BUSINESS Name"

如何更改函数以获得该结果?

ucwords
文档中所述,您可以使用第二个参数:

可选分隔符包含单词分隔符

您可以将符号和定义为附加分隔符。请注意,还应传递默认值(换行符、空格等):


我只是想玩一点,我做了这个

function normalize($str, $disallowAllUppercase = false) {
    $arr = array_map(function ($w) use ($disallowAllUppercase) {
        return ucfirst((strtoupper($w) !== $w || $disallowAllUppercase) ? strtolower($w) : $w);
    }, explode(" ", $str));
    return implode(" ", $arr);
}
你可以在phpsandbox上试试,我把它扔了


它是否满足您的需要?

“另一个企业名称”($DisallowlUppercase为false)
-实际上应该是:
另一个企业名称
,因为
$DisallowlUppercase仍然为false,所以任何大写字符都应该保留。
问题在于
ctype\u upper
。对于
M&S
(应如此),它返回
FALSE
,然后您将其下框,最后将第一个字母上框。一个选项是在使用
ctype_upper
之前去掉所有非A-Z字符。另一个选项如用户2476294在其注释中指出的,是使用
strtoupper($str)!=$str
似乎很有希望,但没有考虑到$disallowlUppercase为true。因为只有字母字符可以是小写或大写,并且这已经用strtoupper实现了,您不能用以下检查替换ctype\u upper方法:
strtoupper($str)=$str
?这应该可以解决这个问题,因为ctype_upper用符号表示为false,尽管您希望它为true,但我认为?欢迎提供指向解决方案的链接,但请确保您的答案在没有它的情况下是有用的:这样,您的其他用户就会知道它是什么以及它为什么存在,然后引用你链接到的页面最相关的部分,以防目标页面不可用。
function normalize($str, $disallowAllUppercase = false) {
    $arr = array_map(function ($w) use ($disallowAllUppercase) {
        return ucfirst((strtoupper($w) !== $w || $disallowAllUppercase) ? strtolower($w) : $w);
    }, explode(" ", $str));
    return implode(" ", $arr);
}