6

Python でコンパイルされた正規表現パターンには、次のことを行うfindallメソッドがあります。

文字列のリストとして、文字列内のパターンの重複しない一致をすべて返します。文字列は左から右にスキャンされ、見つかった順序で一致が返されます。パターンに 1 つ以上のグループが存在する場合は、グループのリストを返します。パターンに複数のグループがある場合、これはタプルのリストになります。空の一致は、別の一致の先頭に触れない限り、結果に含まれます。

Perlでこれを行う標準的な方法は何ですか? 私が考えることができる素朴なアルゴリズムは、「検索と空の文字列への置換が成功している間、[スイート]を実行する」という行に沿っています。もっと良い方法があることを願っています。:-)

前もって感謝します!

4

3 に答える 3

13

/g試合で修飾子を使用します。perlopマニュアルから:

" /g" 修飾子は、グローバル パターン マッチング、つまり、文字列内で可能な限り多くのマッチングを指定します。どのように動作するかは、コンテキストによって異なります。リスト コンテキストでは、正規表現のキャプチャ用括弧に一致する部分文字列のリストを返します。括弧がない場合は、パターン全体が括弧で囲まれているかのように、一致したすべての文字列のリストを返します。

スカラー コンテキストでは、" m//g" を実行するたびに次の一致が検出され、一致する場合は true が返され、それ以上一致しない場合は false が返されます。関数を使用して、最後の一致の後の位置を読み取ったり設定したりできますpos()posの「 」を参照してくださいperlfunc/c一致に失敗すると、通常は検索位置が文字列の先頭にリセットされますが、" " 修飾子 (" " など)を追加することでこれを回避できますm//gc。ターゲット文字列を変更すると、検索位置もリセットされます。

于 2009-01-22T02:04:14.110 に答える
8

//gChris の応答に基づいて構築するには、次のように正規表現をwhileループに入れることがおそらく最も適切です。

my @matches;
while ( 'foobarbaz' =~ m/([aeiou])/g )
{
    push @matches, $1;
}

いくつかの簡単な Python I/O を貼り付けます。

>>> import re
>>> re.findall(r'([aeiou])([nrs])','I had a sandwich for lunch')
[('a', 'n'), ('o', 'r'), ('u', 'n')]

Perl で同等のものを取得するには、構文は次のようになります。

my $matches = [];
while ( 'I had a sandwich for lunch' =~ m/([aeiou])([nrs])/g )
{
    push @$matches, [$1,$2];
}

whileしかし、一般的には、反復する関数が何であれ、おそらくループ自体の中で実行できます。

于 2009-01-22T02:35:09.837 に答える
2

@kyleの回答と同様の内容の初心者向けリファレンス: Perl チュートリアル: 正規表現の使用

于 2009-01-22T02:36:28.070 に答える