6

次のタイプのデータに対して照合しようとしている正規表現があります。各トークンは不明な数のスペースで区切られています。

更新:「テキスト」はほとんどすべての文字にすることができます。これが、.*最初に持っていた理由です。重要なことに、スペースを含めることもできます。

  1. 文章
  2. テキスト 01
  3. テキスト 01/03
  4. テキスト 01 (03 のうち)
  5. テキスト 01-03

「テキスト」、「01」、および「03」を個別のグループとしてキャプチャしたいのですが、「テキスト」以外はすべてオプションです。これまでに私ができる最高のことは次のとおりです。

\s*(.*)\s+(\d+)\s*(?:\s*\(?\s*(?:of|-)\s*(\d+)\s*\)?\s*)

これは #3 ~ #5 に一致し、それらを適切なキャプチャ グループに配置します。?しかし、オプションの後に式の一部を作成するために最後に追加を追加する01と、キャプチャ グループがすべてファンキーになる理由がわかりません。

\s*(.*)\s+(\d+)\s*(?:\s*\(?\s*(?:of|-)\s*(\d+)\s*\)?\s*)?

上記の RegEx は #2 ~ #5 に一致しますが、キャプチャ グループは #2 と #5 のみが正しいです。

これは単純な正規表現のように見えるので、なぜこれほど苦労しているのかわかりません。

これは、これをデバッグするために使用しているオンライン正規表現エバリュエーターへのリンクです: http://regexr.com?2tb64。リンクには、最初の RegEx とテスト データが既に入力されています。

4

3 に答える 3

6

あなたが使用している正規表現ツールを言わなかったので、最も一般的な分母、つまりJavascriptを想定しています。これが機能するものです:

var re = /^\s*(.+?)(?:\s+(\d+)(?:(?:\s+\(?of\s+|-)(\d+)\)?)?)?$/i;

Regexr ツールでこれを機能させるには、必ず「複数行オプション」をオンにしてください。

これは、PHP 構文でも同じです (たくさんの興味深いコメントがあります!)。

$re = '/ # Always write non-trivial regex in free-space mode!
    ^                  # Anchor to start of string.
    \s*                # optional leading whitspace is ok.
    (.+?)              # Text can be pretty much anything.
    (?:                # Group to allow applying ? quantifier
      \s+              # WS separates "Text" from first number.
      (\d+)            # First number.
      (?:              # Group to allow applying ? quantifier
        (?:            # Second number prefix alternatives
          \s+\(?of\s+  # Either " of 03" and " (of 03)",
        | -            # or just a dash  for "-03" case.
        )              # End second number prefix alternatives
        (\d+)          # Second number
        \)?            # Match ")" for " (of 03)" case.
      )?               # Second number is optional.
    )?                 # First numebr is optional.
    $                  # Anchor to start of string.
    /ix';
于 2011-03-19T03:57:08.447 に答える
1

あなたの 2 番目のものは近いです

だから私は作り直しました:regexr、すべて正しいグループに一致するようになりました。

\s*(\w*)\s+(?:\s*(\d+)\s*(?:\s*\(?\s*(?:of|-)\s*(\d+)\s*\)?)?)?
于 2011-03-18T23:13:06.883 に答える
1

これを試してください:
http://regexr.com?2tb67

正規表現は次のようになります。

(\w+?)\s+(\d*)[^\d]*(\d+)

すべての文字に一致し、その後に空白が続きます。次に、すべての数字に一致し、その後に数字以外が続き、残りの数字に一致します。

01 は 3 番目のグループ マッチに含まれるため、2 番目の結果はおそらく理想的ではないことに注意してください。しかし、それはあなたのすべてのケースに一致します。

于 2011-03-18T23:18:18.423 に答える