Reputation: 1145
I wanted to match something from right to left, below is one of such example.
100abababab3x3x3xx1000morewords
If i want to match something between and last xx
and immediate previous ab
and get 3x3x3
I tried something like below , but it matches ababab3x3x3
preg_match('/ab(.*?)xx/',$text,$totmat);
Note : please don't recommend strrev.
Above example is just for illustration , all i wanted to do is match from right to left.
Upvotes: 1
Views: 4077
Reputation: 38502
Not sure this is the most optimized way or not? But this will work for you if you use the combination of Look ahead positive (?=)
and Look behind positive (?<=)
. See regex
<?php
$re = '/\w+(?<=ab)(.*?)(?=xx)/m';
$str = '100abababab3x3x3xx1000morewords';
preg_match_all($re, $str, $matches, PREG_SET_ORDER, 0);
// Print the full matched result
echo $matches[0][1];
DEMO: https://3v4l.org/db69N
Upvotes: 1
Reputation: 876
There are other approaches than a regex to this kind of problem that would be close to twice faster in computing time.
Here for example :
$str = "100abababab3x3x3xx1000morewords";
$result = explode("ab", explode("xx", $str)[0]);
var_dump(end($result));
First occurence of explode split the string in two between the "xx" characters. We're only interested by the left part (Index 0).
Second occurence of explode split the string with the caracters ab. We're only interested by the last occurence of ab. Therefore var_dump(end($result));
prints the expected result.
Upvotes: 0
Reputation: 91428
$str = '100abababab3x3x3xx1000morewords';
preg_match('/ab((?:(?!ab).)*)xx/', $str, $m);
print_r($m);
Output:
Array
(
[0] => ab3x3x3xx
[1] => 3x3x3
)
>Explanation:
ab : literally ab
( : start group 1
(?: : start non capture group
(?!ab) : negative lookahead, make sure we doon't have ab
. : any character but newline
)* : end group, may appear 0 or more times
) : end group 1
xx : literally xx
Upvotes: 0