[英]re.sub fails to execute - even if the regex pattern is found?
考慮一下我在Python 2.7上運行過的示例:
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import re
tstr = r''' <div class="thebibliography">
<p class="bibitem" ><span class="biblabel">
[1]<span class="bibsp"> </span></span><a
id="Xtester"></a><span
class="cmcsc-10">A<span
class="small-caps">k</span><span
class="small-caps">e</span><span
class="small-caps">g</span><span
class="small-caps">c</span><span
class="small-caps">t</span><span
class="small-caps">o</span><span
class="small-caps">r</span>,</span>
<span
class="cmcsc-10">P. D.</span><span
class="cmcsc-10"> H. </span> testöng ... . <span
class="cmti-10">Draftin:</span>
<a
href="http://www.example.com/test.html" class="url" ><span
class="cmitt-10">http://www.example.com/test.html</span></a> (2001).
</p>
</div>
'''
# remove <a id>
tout2 = re.sub(r'''<a[\s]*?id=['"].*?['"][\s]*?></a>''', " ", tstr, re.DOTALL)
# remove class= in <a
regstr = r'''(<a.*?)(class=['"].*?['"])([\s]*>)'''
print( re.findall(regstr, tout2, re.DOTALL)) # finds
print("------") #
print( re.sub(regstr, "AAAAAAA", tout2, re.DOTALL )) # does nothing?
當我運行此命令時-第一個正則表達式已按預期替換/替換(消失了); 然后在輸出中我得到:
[('<a\nhref="http://www.example.com/test.html" ', 'class="url"', ' >')]
...這意味着第二個正則表達式正確編寫了(找到了所有三個部分)-但是,當我嘗試將所有代碼段替換為“ AAAAAAA”時-輸出的那部分沒有任何反應:
------
<div class="thebibliography">
<p class="bibitem" ><span class="biblabel">
[1]<span class="bibsp"> </span></span> <span
class="cmcsc-10">A<span
class="small-caps">k</span><span
class="small-caps">e</span><span
class="small-caps">g</span><span
class="small-caps">c</span><span
class="small-caps">t</span><span
class="small-caps">o</span><span
class="small-caps">r</span>,</span>
<span
class="cmcsc-10">P. D.</span><span
class="cmcsc-10"> H. </span> testöng ... . <span
class="cmti-10">Draftin:</span>
<a
href="http://www.example.com/test.html" class="url" ><span
class="cmitt-10">http://www.example.com/test.html</span></a> (2001).
</p>
</div>
顯然,正如我期望的那樣,這里沒有“ AAAAAAA”。
問題是什么,我應該怎么做才能讓sub
替換顯然已找到的匹配項?
為什么不使用HTML解析器來解析和修改HTML
。
例如,使用BeautifulSoup
和replace_with()
:
from bs4 import BeautifulSoup
data = """Your html here"""
soup = BeautifulSoup(data)
for link in soup('a', id=True):
link.replace_with('AAAAAA')
print(soup.prettify())
這會將所有具有id
屬性的鏈接替換為AAAAAA
文本:
<div class="thebibliography">
<p class="bibitem">
<span class="biblabel">
[1]
<span class="bibsp">
</span>
</span>
AAAAAA
<span class="cmcsc-10">
...
另請參閱:
由於誤用了re.sub方法,因此無法進行替換。如果您查看文檔,請執行以下操作:
re.sub(pattern, repl, string, count=0, flags=0)
但是在代碼中,您將“標志”放在“計數”位置。 這就是為什么re.DOTALL
標志被忽略,原因是它位於錯誤的位置。
由於您不需要使用count參數,因此可以刪除re.DOTALL
標志並使用內聯修飾符:
regstr = r'''(?s)(<a.*?)(class=['"].*?['"])([\s]*>)'''
但是,使用bs4之類的東西可能更方便。 (如您在@alecxe答案中所見)。
這很簡單:Python標准庫參考說語法或re.sub
是: re.sub(pattern, repl, string, count=0, flags=0)
。 因此,您的最后一個子實際上是(如re.DOTALL
== 16):
re.sub(regstr, "AAAAAAA", tout2, count = 16, flags = 0 )
當您需要時:
re.sub(regstr, "AAAAAAA", tout2, flags = re.DOTALL )
最后一個子效果很好...
問題是-您的論點錯了 。
Python 2.7來源:
def re.sub(pattern, repl, string, count=0, flags=0):
//code
在這里,您的參數re.DOTALL被視為count參數。
FIX:使用re.sub(regstr, "AAAAAAA", tout2, flags=re.DOTALL )
代替
注意:如果您嘗試將編譯與正則表達式一起使用,則sub可以正常工作。
好吧,在這種情況下,顯然,我應該使用一個已編譯的regex對象(而不是直接通過re.
模塊調用),並且一切似乎都可以工作(甚至可以使用反向引用)-但我仍然不明白為什么這個問題發生了嗎? 了解最終為什么會很好...無論如何,這是經過更正的代碼段:
# remove <a id>
tout2 = re.sub(r'''<a[\s]*?id=['"].*?['"][\s]*?></a>''', " ", tstr, re.DOTALL)
# remove class= in <a
regstr = r'''(<a.*?)(class=['"].*?['"])([\s]*>)'''
pat = re.compile(regstr, re.DOTALL)
#~ print( re.findall(regstr, tout2, re.DOTALL)) # finds
print( pat.findall(tout2)) # finds
print("------") #
# re.purge() # no need
print( pat.sub(r'\1AAAAAAA\3', tout2, re.DOTALL )) # does nothing?
...這是輸出:
[('<a\nhref="http://www.example.com/test.html" ', 'class="url"', ' >')]
------
<div class="thebibliography">
<p class="bibitem" ><span class="biblabel">
[1]<span class="bibsp"> </span></span> <span
class="cmcsc-10">A<span
class="small-caps">k</span><span
class="small-caps">e</span><span
class="small-caps">g</span><span
class="small-caps">c</span><span
class="small-caps">t</span><span
class="small-caps">o</span><span
class="small-caps">r</span>,</span>
<span
class="cmcsc-10">P. D.</span><span
class="cmcsc-10"> H. </span> testöng ... . <span
class="cmti-10">Draftin:</span>
<a
href="http://www.example.com/test.html" AAAAAAA ><span
class="cmitt-10">http://www.example.com/test.html</span></a> (2001).
</p>
</div>
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.