替换php保留案例中的单词

时间:2017-07-27 00:53:41

标签: php regex

如何替换一些' 整个词'对于其他人保持相同的上限(下限,第一或全部)和单数/复数的源词?

如果我有这个:

$text="This is a text about animals Word1 and Letters1. 
We also talk about animals words2, letter2 and WORDS3, LETTERS3. 
And text woRd4, LEtter4 and LETTEr5 and wordpress";

$replacements=['word'=>'cat','letter'=>'dog'];

我希望得到:

$text="This is a text about animals Cat1 and Dogs1. 
We also talk about animals cats2, dog2 and CATS3, DOGS3. 
And text woRd4, LEtter4 and LETTEr5 and wordpress";

总结:

我有一个词和一个替代词:例如,' letter'和“狗”,我想:

  1. 使用小写替换更改与小写字母匹配的所有单词:' letter'通过' dog'。
  2. 将大写字母中与该单词匹配的所有单词更换为大写字母:' LETTER'通过' DOG'。
  3. 将所有与该单词匹配的单词改为大写字母的第一个字母,将其替换为大写字母的第一个字母:' Letter' by' Dog'。
  4. 我想在数组中只使用一个组合,而不是三个组合,因为从配置文件中读取数组:

    我想在配置中写这个:

    $replacements=['word'=>'cat','letter'=>'dog'];

    而不是这个:

    $replacements=['word'=>'cat','Word'=>'Cat','WORD'=>'CAT','letter'=>'dog', 'Letter'=>'Dog','LETTER'=>'DOG'];

    我找到的最佳解决方案是:

    $text="This is a text about animals Word1 and Letters1. 
        We also talk about animals words2, letter2 and WORDS3, LETTERS3. 
        And text woRd4, LEtter4 and LETTEr5";
    
    function replace($replacements, $text)
    {
        $_replacements=[];
    
        // Add the three possible patterns
        foreach($replacements as $search=>$replace)
        {
            $_replacements[strtolower($search)]=strtolower($replace);
            $_replacements[strtoupper($search)]=strtoupper($replace);
            $_replacements[ucfirst(strtolower($search))]=ucfirst(strtolower($replace));
        }
    
        return str_replace(array_keys($_replacements), array_values($_replacements), $text);
    }
    
    echo(replace($replacements, $text));
    

    然而,这个解决方案取代了CatPress的WordPress :(

    是否有更好的和/或更有效的解决方案?使用正则表达式的任何解决方案?

    PS:您可以在此处测试我的代码:http://sandbox.onlinephpfunctions.com/code/aa37de86c01228b82aee0622c6b17c5cf9f08241

    PS:此行:And text woRd4, LEtter4 and LETTEr5表示所有其他可能的案例组合都不重要。

    PS:我在stackoverflow中发现的类似问题是关于格式化和突出显示,其解决方案不适用于这种情况(或者我不知道如何应用它)

1 个答案:

答案 0 :(得分:1)

处理不规则复数的版本:

$text = 'This is a text about animals, Children, Word1 and Letters1. 
We also talk about animals words2, letter2 and WORDS3, LETTERS3. 
And text woRd4, LEtter4 and LETTEr5';

// replacements
$regular = [ 'word' => 'cat', 'letter' => 'dog', 'animal' => ['child', 'children'] ];
$nonregular = [ 'child' => 'animal', 'children' => 'animals' ];

$result = preg_replace_callback('~[a-z]+(?:(?<=(s)))?~i', function ($m) use ($regular, $nonregular) {
    $lower = strtolower($m[0]);
    $rep = $m[0];
    if ( isset($nonregular[$lower]) ) {
        $rep = $nonregular[$lower];
    } elseif ( isset($regular[$lower]) ) {
        $rep = is_array($regular[$lower]) ? $regular[$lower][0] : $regular[$lower];
    } elseif ( isset($m[1]) ) {
        $sing = substr($lower, 0, -1);
        if ( isset($regular[$sing]) )
            $rep = is_array($regular[$sing]) ? $regular[$sing][1] : $regular[$sing] . 's';
    } else {
        return $rep;
    }

    if ( $m[0] == $lower )
        return $rep;
    elseif ($m[0] == strtoupper($lower) )
        return strtoupper($rep);
    elseif ( $m[0] == ucfirst($lower) )
        return ucfirst($rep);

    return $rep;
}, $text);

echo $text, PHP_EOL, PHP_EOL, $result;

demo

随意组织具有复数类别的替换数组并编写unicode版本。