我正在尝试用PHP翻译一个javascript脚本。到目前为止一切都很顺利,但我偶然发现了一些我一无所知的代码:
while (match = someRegex.exec(text)) {
m = match[0];
if (m === "-") {
var lastIndex = someRegex.lastIndex,
nextToken = someRegex.exec(parts.content);
if (nextToken) {
...
}
someRegex.lastIndex = lastIndex;
}
}someRegex变量如下所示:
/[^\\-]+|-|\\(?:[0-3][0-7]{0,2}|[4-7][0-7]?|x[0-9A-Fa-f]{2}|u[0-9A-Fa-f]{4}|c[A-Za-z]|[\S\s]?)/gexec应该等同于PHP中的preg_match_all:
preg_match_all($someRegex, $text, $match);
$match = $match[0]; // I get the same results so it works
foreach($match as $m){
if($m === '-'){
// here I don't know how to handle lastIndex and the 2nd exec :(
}
}发布于 2013-03-26 23:43:57
我根本不会使用lastIndex的魔力--本质上是对每个索引执行两次正则表达式。如果你真的想这样做,你需要在preg_match_all中设置PREG_OFFSET_CAPTURE标志,这样你就可以获得位置,添加捕获长度,并将其用作下一个preg_match偏移量。
最好使用这样的东西:
preg_match_all($someRegex, $text, $match);
$match = $match[0]; // get all matches (no groups)
$len = count($match);
foreach($match as $i=>$m){
if ($m === '-') {
if ($i+1 < $len) {
$nextToken = $match[$i+1];
…
}
…
}
…
}发布于 2013-03-26 23:16:19
实际上,exec并不等同于preg_match_all,因为exec在第一次匹配时停止(g修饰符仅将lastIndex值设置为遍历字符串)。它等同于preg_match。因此,您可以找到第一个匹配项,通过$array参数获取该值(包含在$flags中)的偏移量,然后通过设置偏移量(最后一个参数)继续搜索。
我猜第二次执行不会有问题,因为您将执行与javascript版本完全相同的操作。
注意,我还没有尝试过这个循环,但是一旦您弄清楚了preg_match如何使用可选参数(我将运行一些测试),它就会变得非常简单。
$lastIndex = 0;
while(preg_match($someRegex, $text, $match, PREG_OFFSET_CAPTURE, $lastIndex) {
$m = $match[0][0];
$lastIndex = $match[0][1] + strlen($m); //thanks Bergi for the correction
if($m === '-') {
// assuming the $otherText relate to the parts.content thing
if(preg_match($someRegex, $otherText, $secondMatch, 0, $lastIndex)) {
$nextToken = $secondMatch[0];
...
}
}
}我想应该就是这样了(请原谅我的小错误,我已经有一段时间没做php了)。
https://stackoverflow.com/questions/15640184
复制相似问题