7

sp { ...{...}... }中括弧がネストできるようなテキストを一致させようとしています。これは私がこれまでに持っているものです:

my $regex = qr/
(                   #save $1
    sp\s+           #start Soar production
    (               #save $2
        \{          #opening brace
        [^{}]*      #anything but braces
        \}          #closing brace  
        | (?1)      #or nested braces
    )+              #0 or more
)
/x;

次のテキストと一致させることができません: sp { { word } }. 私の正規表現の何が問題なのか誰にもわかりますか?

4

2 に答える 2

6

これはText::Balanced、この種の非常に便利なコア モジュールである、あまり使用されていない の場合です。区切られたシーケンスの開始が最初に検出/設定されることに依存しているposため、通常は次のように呼び出します。

#!/usr/bin/env perl

use strict;
use warnings;

use Text::Balanced 'extract_bracketed';

sub get_bracketed {
  my $str = shift;

  # seek to beginning of bracket
  return undef unless $str =~ /(sp\s+)(?={)/gc;

  # store the prefix
  my $prefix = $1;

  # get everything from the start brace to the matching end brace
  my ($bracketed) = extract_bracketed( $str, '{}');

  # no closing brace found
  return undef unless $bracketed;

  # return the whole match
  return $prefix . $bracketed;
}

my $str = 'sp { { word } }';

print get_bracketed $str;

修飾子を含む正規表現gcは、一致の終点がどこにあるかを記憶するように文字列に指示し、extract_bracketedその情報を使用してどこから開始するかを認識します。

于 2012-10-04T04:28:04.180 に答える
6

多くの問題があります。再帰ビットは次のようになります。

(
   (?: \{ (?-1) \}
   |   [^{}]+
   )*
)

すべて一緒に:

my $regex = qr/
   sp\s+
   \{
      (
         (?: \{ (?-1) \}
         |   [^{}]++
         )*
      )
   \}
/x;

print "$1\n" if 'sp { { word } }' =~ /($regex)/;
于 2012-10-04T03:49:27.847 に答える