2012-01-08 11 views
5

私はこの正規表現を理解しようとしています、あなたは私を助けることができますか? (?s) 私は理解していない正規表現

  • なぜダブル\\}前に:

    (?s)\\{\\{wotd\\|(.+?)\\|(.+?)\\|([^#\\|]+).*?\\}\\} 
    
    • 私は本当にDOTALLの意味を理解していませんか?
    • これは正確に何を意味:(.+?)を(我々はこれを読むべきよう:?.、その後、+が、その後?は、この正規表現は、文字列からである.+
  • +4

    、それは文字列リテラルであります?たとえば、パターンp = Pattern.compile( "(?s)\\ {\\ {wotd \\ |(。+?)\\ |(。+?)\\ |([^#\\ |] +)。*?\\} \\} ");'?文字列リテラルと正規表現の両方でバックスラッシュがエスケープされているので、 '\\ {'を解釈するためには、\\ {"'(その場合は '\\'がパターンコンパイラは以下の '{')をエスケープする単一のバックスラッシュまたはパターンファイルコンパイラが*エスケープされたバックラッシュとそれに続く '\\ {' {'。 –

    +0

    '。+?'は貪欲でない(「嫌な」) '+'演算子です。 '\\\'はリテラルのバックスラッシュを意味し、正規表現がJavaでJava文字列に埋め込まれていると仮定すると、最初の '\\'は2番目の文字をエスケープします。 –

    答えて

    8

    の結果への対応、.に作用します。 「標準的な」正規表現は次のとおりです。

    (?s)\{\{wotd\|(.+?)\|(.+?)\|([^#\|]+).*?\}\} 
    

    DOTALL修飾子はドットでも改行文字を一致させることができることを意味しますが、そう少なくともジャワで、文字クラスを補完することができます。すなわち[^a]意志aではない各文字に一致し、改行が含まれています。いくつかの正規表現エンジンは補完された文字クラスの改行にマッチしません(これはバグと見なすことができます)。

    +?*?は、一般的には避けるべきです。つまり、これらの文字が正規表現の次の要素を満たすことができるかどうかを見たいと思っているキャラクターの前に、前進しなければならないということです。

    {}の前に\が付いているというのは、{...}が繰り返し数量子{n、m}であり、nとmが整数であるからです。

    また、[^#\|]という文字クラスのパイプ|をエスケープすることは役に立たず、単に[^#|]と書くことができます。

    最後に、.*?は残りのフィールドを飲み込むようです。より良い選択肢は、normal* (special normal*)*パターンを使用することです。normal[^|}]で、special\|です。

    ここでは、遅延固定子、「固定」文字クラス、および修正された終端を使用しない正規表現を示します。ドットがもはや使用されていないので、DOTALL修飾子は、同様に消えていることに注意してください:ステップバイ

    \{\{wotd\|([^|]+)\|([^|]+)\|([^#|]+)[^|}]*(?:\|[^|}]*)*\}\} 
    

    ステップ:あなたがこれを見ソースで

    \{\{   # literal "{{", followed by 
    wotd   # literal "wotd", followed by 
    \|   # literal "|", followed by 
    ([^|]+)  # one or more characters which are not a "|" (captured), followed by 
    \|   # literal "|", followed by 
    ([^|]+)  # one or more characters which are not a "|" (captured), followed by 
    \|   # literal "|", followed by 
    ([^#|]+)  # one or more characters which are not "|" or "#", followed by 
    [^|}]*  # zero or more characters which are not "|" or "}", followed by 
    (?:   # begin group 
        \|   # a literal "|", followed by 
        [^|}]*  # zero or more characters which are not "|" or "}" 
    )   # end group 
    *   # zero or more times, followed by 
    \}\}   # literal "}}" 
    
    +0

    遅延量指定子を避けることをお勧めするのはなぜですか? – Lucero

    +0

    正規表現は元の正規表現と同じではないことに注意してください。オリジナルはあなたのものではない多くの文字列にマッチします。私が推測しなければならないのは、あなたのバージョンが正規表現ライターの本来の意図に近いと推測しますが、要件が何であるか分からず、確実に知る方法はありません。 (バージョンによっては '.'が使用されないので、あなたのバージョンから'(?s) 'を削除することもできます) – ruakh

    +0

    最後の'。*? 'は意味を持ちません。他のパイプまた、エスケープされます(あなたの最後の正規表現が落ちます)。正規表現は、パイプがソートのフィールド区切り文字として使用される文字列を探しています: '{wotd | field1 | field2 | some_stuff#おそらくコメント}' – user268396

    関連する問題