php - Preg replace with array of patterns not working as expected

240

Why would this code

 $my_replacements = array("my dog", "doga");
 $my_string = "doga my dog test";
 $my_patterns = array_map(function($my_text) { return "/(^|[\n\r\f\t \.\,])" . trim($my_text) . "([\n\r\f\t \.\,]|$)/iu"; }, $my_replacements);
 $replaced_string = preg_replace($my_patterns, '', $my_string);
 echo $replaced_string;

returndogatest instead oftest?

but if my_string is changed to"my dog doga test", it replaces correctly both elements in my_replacements?

What I want to accomplish is that, given a string, find all the strings that are in $my_replacements and delete them from the string. Taking into account the /u modifier and /i modifier or a preg_replace, because it can happen that the substring is in uppercase, and it has to be deleted either way.

612

Answer

Solution:

Because your replacements are transformed to the following regexps:

/(^|[\n\r\f\t \.\,])my dog([\n\r\f\t \.\,]|$)/iu
/(^|[\n\r\f\t \.\,])doga([\n\r\f\t \.\,]|$)/iu

After the first regex is applied to the source string"my dog doga test" - it cuts off thedog doga with spaces around it. So you getdogatest.

And after that the second regex cannot match anything, because it expects thedoga to be enclosed by beginning or the end of the string, a space or punctuation. But in your case it's in the beginning of the string (true) but there is no a space, punctuation or end of the string after (false).

That's why the second regex doesn't modify the string and you getdogatest as a final result.

Straightforward solution without regexes:

 $my_replacements = array("my dog", "doga");
 $my_string = "doga my dog test";
 $replaced_string = str_replace($my_replacements, '', $my_string);
 echo $replaced_string;

The kind @Asad created a codepad demo of the script: http://codepad.org/ywbZR1i8

578

Answer

Solution:

Is there a reason of why you don't use str_replace? If yes, you can use
$my_replacements = array("doga", "my dog");
instead of
$my_replacements = array("my dog", "doga");

Reason: after "doga" is replaced with '' in your string, this becomes "dogatest". So, doga with spaces (as you defined the regular exp) is not there. You could also make the replace with " " instead of '',
$replaced_string = preg_replace($my_patterns, ' ', $my_string);
And then trim and replace all multiple spaces with one space (a simple recursive replace).

People are also looking for solutions to the problem: php - Symfony2 POST Request Required, Receiving GET Instead

Source

Didn't find the answer?

Our community is visited by hundreds of web development professionals every day. Ask your question and get a quick answer for free.

Ask a Question

Write quick answer

Do you know the answer to this question? Write a quick response to it. With your help, we will make our community stronger.

Similar questions

Find the answer in similar questions on our website.