2016-10-18 9 views
1

括弧の前にいくつかの単語を探したい文字列があります。文字列があるとしましょう -%sは正規表現で奇妙な動作を示しています

私はせいぜい5つのワードをキャプチャしたい

「はまた、うつ病症候群(DS)を持っている大腸癌(CRC)を有する、世界の多くの人々があります」かっこの前に。私は括弧の中にある略語のリストacronym_listを持っています - [(crc), (ds)]。だから私は、次のコードを使用しています -

acrolen=5 
rt=[] 
for acro in acronym_list: 
    find_words= re.findall('((?:\w+\W+){1,%d}%s)' %(acrolen, acro), text, re.I) 
    for word in find_words: 
      rt.append(word) 
print rt 

をしかし、これは、この結果を与える -

('the world having colorectal cancer (crc', 'crc') 
('also have the depression syndrome (ds', 'ds') 

私は正規表現を使用する場合のに対して -

find_words= re.findall('((?:\w+\W+){1,%d}\(crc\))' %(acrolen),s, re.I)

を次に見つけることができまさに私が欲しいもの -

the world having colorectal cancer (crc) 

質問です - 私はきちんとそう第一正規表現を使用するにはどうすればよい(..頭字語などを繰り返し、その周りに不要な括弧を持つ)、ここでとても大幅に異なるように正規表現マッチを引き起こして文字列を

%sを使用する理由正規表現で毎回正確な文字列を入力するのではなく、ループを使用してプロセスを自動化することができますか?

答えて

1

あなたが渡す変数が、正規表現のパターン内でリテラルテキストとして使用されるように正しくエスケープされていることを確認する必要があります。 re.escape(acro)を使用します。

import re 
text = "there are many people in the world having colorectal cancer (crc) who also have the depression syndrome (ds)" 
acrolen=5 
rt=[] 
acronym_list = ["(crc)", "(ds)"] 
for acro in acronym_list: 
    p = r'((?:\w+\W+){1,%d}%s)' %(acrolen, re.escape(acro)) 
    # Or, use format: 
    # p = r'((?:\w+\W+){{1,{0}}}{1})'.format(acrolen, re.escape(acro)) 
    find_words= re.findall(p, text, re.I) 
    for word in find_words: 
     rt.append(word) 
print rt 

は、またPython demo

を参照してくださいあなたは何のキャプチャグループは、パターンで定義されていない場合re.findallが一致値を返します、キャプチャグループでパターン全体を囲む必要はありません。

あいまいな状況を避けるために正規表現パターンを定義する場合は、生の文字列リテラルを使用することもお勧めします。

+0

ありがとう、これは非常に有益でした。しかし、{{1、{0}}} {1}はどのように '{1、%d}%s 'と同じように働いたのか説明できますか? – user1993

+1

フォーマット文字列では、 '{n}'はメソッドの引数のプレースホルダです。リテラルブレースを示すには、2倍にする必要があります。 –

関連する問題