3

JavaScript と PHP が次の正規表現を処理する方法の違いを見つけて混乱しています。

JavaScript では、

'foobar'.replace(/(?=(bar))/     , '$1');
'foobar'.replace(/(?=(bar))?/    , '$1');
'foobar'.replace(/(?:(?=(bar)))?/, '$1');

それぞれ、

foobarbar
foobar
foobar

このjsFiddleに示すように。

ただし、PHP では、

echo preg_replace('/(?=(bar))/', '$1', "foobar<br/>");
echo preg_replace('/(?=(bar))?/', '$1', "foobar<br/>");
echo preg_replace('/(?:(?=(bar)))?/', '$1', "foobar<br/>");

その結果、

foobarbar

Warning: preg_replace() [function.preg-replace]: Compilation failed: nothing to repeat at offset 9 in /homepages/26/d94605010/htdocs/lz/writecodeonline.com/php/index.php(201) : eval()'d code on line 2
foobarbar

警告についてはそれほど心配していません。しかし、JavaScript では、先読みアサーションが PHP よりも「遅延」しているようです。違いはなぜですか?これはいずれかのエンジンのバグですか? 理論的により「正しい」のはどれですか?

4

1 に答える 1

2

実際の違いは非常に単純です。

JavaScript では、フラグ (グローバル)を使用しない限りreplace 、最初の一致のみを置き換えます。 PHP では、すべての一致を置き換えます。/g
preg_replace

3 番目のパターン は(?:(?=(bar)))?、すべての位置で空の文字列に一致し"bar"いくつかの位置でキャプチャできます。フラグがない/g場合、文字列の先頭で 1 回だけ一致します。

のようなより見やすい置換文字列を使用していれば、違いが簡単にわかります[$1]

PHP の例: http://ideone.com/8Mjg6
JavaScript の例、なし/g: http://jsfiddle.net/qKb4b/3/
JavaScript の例、あり/g: http://jsfiddle.net/qKb4b/2/

また、「怠惰」は正規表現では別の概念であり、この質問とは関係ありません。

于 2012-09-15T17:10:34.920 に答える