私はあなたのコードで何が起こるかを説明します:
import re
file = open('f1.txt')
fixed = open('fnew.txt','w')
text = file.read()
match = re.compile('<.*>')
for unwanted in text:
fixed_doc = match.sub(r' ',text)
fixed.write(fixed_doc)
命令text = file.read()
はtext
名前付きの型文字列の対象テキストを作成します。
私は太字の文字テキストをOBJECTで表現し、text
でこのオブジェクトの名前== IDENTIFIERを表すことに注意してください。
命令for unwanted in text:
の結果として、テキストオブジェクトによって参照される各文字に識別子unwanted
が連続して割り当てられます。
また、re.compile('<.*>')
は(私はpersonnalyコンパイルを呼び出す)タイプRegexObjectのオブジェクト正規表現又は単に正規表現、<.*>
あるのみ正規表現パターン)を作成します。
match
というコンパイル済みの正規表現オブジェクトを割り当てます。match
はすでに一般的な正規表現オブジェクトのメソッドの名前であり、特にあなたが作成したメソッドの名前であるため、非常に悪いことです。match.match
エラー。
match
ものモジュールの機能の名前です。
あなたの特定のニーズにこの名前を使用すると、非常に混乱します。あなたはそれを避けなければなりません。
ファイルf1のファイルハンドラの名前としてfile
を使用した場合、同じ欠陥があります。 file
はすでにその言語で使用されている識別子なので、それを避けなければなりません。
今、この悪い名前の試合オブジェクトが定義され、命令fixed_doc = match.sub(r' ',text)
は、交換r' '
とテキストに正規表現一致で見つかったすべての出現箇所を置き換えます。
' '
の代わりにr' '
と書くのは完全に余計です。' '
には絶対にエスケープする必要がないため、正規表現の問題で文字列を書く必要があるたびに生の文字列を書くことは、心配している人々の流行です。そのため、ドット記号「欲張っ<
、それが改行文字である場合を除き、>
との間に位置するすべての文字を食べる」を意味するそのパターン<.+>
の
は、出現箇所は試合によってテキストにcatched各ラインまでです最後は>
です。
unwanted
という名前はこの命令には表示されないため、テキストの各文字に対して順番に実行される操作と同じです。つまり、興味深いものはありません。
プログラムの実行を分析するには、コードにいくつかの印刷指示を入れて、何が起こるかを理解する必要があります。たとえば、print repr(fixed_doc)
を実行すると、これを繰り返し印刷すると表示されます:' \n \n \n '
。私が言ったように、何も面白くない。
コードにもう1つのデフォルトがあります。ファイルを開いても、それらをシャットダウンしません。ファイルを閉じることは必須です。そうでなければ、この必要性を理解する前に私が個人的にいくつかのコードで見たような奇妙な現象が起こる可能性があります。一部の人々はそれが義務ではないふりをしているが、それは間違っている。
ところで、ファイルを開いたり閉じたりする方が良い方法は、with
ステートメントを使用することです。あなたは心配することなくすべての仕事をします。
。
だから、今私はあなたの最初の問題のためのコードを提案することができ、次のよう
import re
def ripl(mat=None,li = []):
if mat==None:
li[:] = []
return
if mat.group(1):
li.append(mat.span(2))
return ''
elif mat.span() in li:
return ''
else:
return mat.group()
r = re.compile('</[^>]+>'
'|'
'<([^>]+)>(?=.*?(</\\1>))',
re.DOTALL)
text = '''<something @37>
<name>George <wxc>Washington</name>
<a23c>Joe </zazaza>Taylor</a23c>
</something @37>'''
print '1------------------------------------1'
print text
print '2------------------------------------2'
ripl()
print r.sub(ripl,text)
print '3------------------------------------3'
結果
1------------------------------------1
<something @37>
<name>George <wxc>Washington</name>
<a23c>Joe </zazaza>Taylor</a23c>
</something @37>
2------------------------------------2
George <wxc>Washington
Joe </zazaza>Taylor
3------------------------------------3
原理は次のとおりです。
正規表現は、タグを検出すると、
- 終了タグの場合は と一致します。開始タグの場合は、対応する終了タグがどこかにある場合にのみ一致しますさらにテキスト
正規表現のメソッドr
は、置換を実行するために関数ripl()
を呼び出します。
一致が開始タグ(対応する終了タグによってテキストのどこかに続く、正規表現の構築によって必要な場合)の場合、ripl()
は''
を返します。
一致が終了タグである場合、ripl()
は、この終了タグが以前に検出されたテキストのみが前の開始タグの対応する終了タグである場合のみ、''
を返します。これは、開始タグが検出されて一致するたびに、対応する終了タグのスパンのスパンをリストに記録することによって可能になる。
録画リスト、それは微妙だから李は、(、undertsandするデフォルト引数のfunctionningを参照してください、それは常に機能ripl()
の各呼び出しで使用されているのと同じリストだという順番でデフォルトの引数として定義されています)。
デフォルトの引数を受け取るパラメータとしてli
を定義した結果、リストオブジェクトはは、いくつかのテキストを連続して分析する場合にいくつかのテキストを分析するときに記録されたすべてのスパンを保持します。リストliが過去のテキストマッチの範囲を保持するのを避けるには、リストを空にする必要があります。私は最初のパラメータは、正規表現のsub()
メソッドでそれを使用する前に引数なしでripl()
を呼び出すことができるデフォルトの引数None
:で定義されるように関数を書いた。
次に、それを使用する前にripl()
と書く必要があります。
。
あなたは、あなたの質問に示した正確な結果を得るために、テキストの改行を削除したい場合は、コードがに変更する必要があります。
import re
def ripl(mat=None,li = []):
if mat==None:
li[:] = []
return
if mat.group(1):
return ''
elif mat.group(2):
li.append(mat.span(3))
return ''
elif mat.span() in li:
return ''
else:
return mat.group()
r = re.compile('(*\n *)'
'|'
'</[^>]+>'
'|'
'<([^>]+)>(?=.*?(</\\2>)) *',
re.DOTALL)
text = '''<something @37>
<name>George <wxc>Washington</name>
<a23c>Joe </zazaza>Taylor</a23c>
</something @37>'''
print '1------------------------------------1'
print text
print '2------------------------------------2'
ripl()
print r.sub(ripl,text)
print '3------------------------------------3'
結果
1------------------------------------1
<something @37>
<name>George <wxc>Washington</name>
<a23c>Joe </zazaza>Taylor</a23c>
</something @37>
2------------------------------------2
George <wxc>WashingtonJoe </zazaza>Taylor
3------------------------------------3
こんにちは。最初の問題は、タグのように見えるものをすべて削除するか、実際にマークアップ言語の要素を定義するタグですか?私は正しい意味で「要素」という単語を使用します。つまり、「開始タグ+要素の内容+終了タグ」を意味します。 - また、ファイルfの内容を公開しているので、そこに改行が入っています。あなたが望む結果として示しているのは、改行がもうない文字列です。それは本当にあなたが望んでいるのか、構造化を線で維持したいと思いますか? – eyquem
[]にはない値の場合はどうしますか?現在のところ、ボイドリストには何もないので意味がありません。あなたはファイルの比較として何をしたいですか?非常に明確ではありません – eyquem