2011-02-10 15 views
5

私は*にマッチする正規表現が必要なプロジェクトに取り組んでいます。スペースやタブを1〜4つ続け、その後にテキスト行を続けます。今はテスト目的のためにlookbehindの後に*を使用しています。しかし、私は明示的に1つ、2つ、または4つのスペース/タブに一致させることができますが、1-4ではできません。私は、次のブロック数量範囲がlookbehindで機能していない

* test line here 
* Second test 
* Third test 
* Another test 

に対してテストだとこれらは私が交換した場合、私は同じだけの期待どおりに動作し、2行目と一致する(?<=(\*[ \t]{3})).*を、テストしてる2パターンある3と1、2または4しかし、もし私はそれを次のパターンを形成する1,400に置き換えます(?<=(\*[ \t]{1,4})).*それはもはや行のいずれとも一致しません。正直なところ、なぜそれを理解できません。私は成功なしでグーグルで試してみました。私はg(lobal)フラグを使用しています。

答えて

5

PHPは、多くの味のように、可変長のlookbehindをサポートしていません。唯一のサポートは、lookbehindのトップレベルでの代替番号|)です。 ?でもパターンを破る可能性があります。

(?<=\*[ \t]|\*[ \t]{2}|\*[ \t]{3}|\*[ \t]{4}).* 

以上、グループのために後読みを中止:代替が使用することです

\*[ \t]{1,4}(.*) 

あなたは試合の重複持っているように、それはいないようですので、これは、あなたのために働く必要がありますとにかく

マニュアルから:

戻り読み表明の内容は、それが一致するすべての文字列が固定長を持たなければならないよう制限されています。しかし、いくつかの選択肢がある場合、それらはすべて同じ固定長を持つ必要はありません。したがって(?< = bullock | donkey)は許可されますが、(?<!dogs?| cats?)コンパイル時にエラーが発生します。異なる長さの文字列にマッチするブランチは、ルックバックヘッダアサーションの最上位レベルでのみ許可されます。

出典:http://www.php.net/manual/en/regexp.reference.assertions.php

+1

また、正規表現はまだOPはおそらく望んでないだろうことを言及する価値があるかもしれない - * 'うまくスペースにマッチします'ので、それは喜ん以上の4つのスペースにマッチします。 –

+1

@Tim - それは良い点ですが、 '。* 'は、OPが奇妙な動作と見なす単純な例です。面白いのは背後にあります。 – Kobi

+0

ありがとう、私はそれを見落とした。ちなみに、RegexBuddyは '{1,4}'については不平を言っていません(無限の量子ではなく、この有限の量子ではありません)。 –

関連する問題