2011-09-05 4 views
2

일부 HTML 파일을 python + lxml로 처리 중입니다. 그 중 일부는 MS Word로 편집되었으며, 예를 들어 <p> 태그는 <o:p>&nbsp</o:p>으로 작성되었습니다. IE와 Firefox는 이러한 MS 태그를 실제 <p> 태그로 해석하지 않으며 <o:p> 태그 전후에 줄 바꿈을 표시하지 않으며 원래 편집자가 파일을 형식화 한 방법입니다. nbsp 주변에는 공백이 없어야합니다.Python + lxml : 태그의 네임 스페이스를 찾는 방법은 무엇입니까?

1xml은 깔끔하고 HTML 파일을 처리 한 후에는 <o:p> 태그가 모두 <p> 태그로 변경되었습니다. 불행하게도이 두 브라우저를 모두 정리하면 모든 nbsp의 줄 바꿈이 표시되어 원래의 서식이 깨집니다.

제 생각에는 모든 <o:p> 태그를 탐색하여 태그를 제거하거나 .text 속성을 상위 .text 속성에 추가하는 것입니다. 즉, <o:p> 태그 마커를 제거하십시오.

from lxml import etree 
import lxml.html 
from StringIO import StringIO 

s='<p>somepara</p> <o:p>msoffice_para</o:p>' 

parser = lxml.html.HTMLParser() 
html=lxml.html.parse(StringIO(s), parser) 

for t in html.xpath("//p"): 
    print "tag: " + t.tag + ", text: '" + t.text + "'" 

결과는 다음과 같습니다

tag: p, text: 'somepara' 
tag: p, text: 'msoffice_para' 

그래서, lxlm 태그 마커의 네임 스페이스 이름을 제거합니다. 어떤 <p> 태그가 어떤 네임 스페이스의 태그인지 알 수있는 방법이 있습니까? <o:p> 태그 만 제거 할 수 있습니까?

감사합니다.

답변

1

HTML 사양 : "The HTML syntax does not support namespace declarations". 그래서 나는 lxml.html.HTMLParser이 네임 스페이스를 제거하거나 무시한다고 생각합니다.

그러나 BeautifulSoup은 HTML을 다르게 구문 분석하므로 유용 할 것이라고 생각했습니다.

import lxml.html.soupparser as soupparser 
import lxml.html 
import io 
s='<p>somepara</p> <o:p>msoffice_para</o:p>' 
html=soupparser.parse(io.BytesIO(s)) 

BeautifulSoup로 네임 스페이스를 제거하지 않지만, 둘은 같은 네임 스페이스를 인식하지 않습니다 당신은 또한 BeautifulSoup로 설치 한 경우,이 같은 LXML으로 BeautifulSoup로 파서를 사용할 수 있습니다. 대신, 태그 이름의 일부일뿐입니다. 말을하는 것입니다

,

html.xpath('//o:p',namespaces={'o':'foo'}) 

이 작동하지 않습니다. 그러나이 해결 방법은/

for t in html.xpath('//*[name()="o:p"]'):  
    print "tag: " + t.tag + ", text: '" + t.text + "'" 

는 HTML이 실제로 잘 형성되면, 대신 etree.XMLParser을 사용할 수

tag: o:p, text: 'msoffice_para' 
0

를 산출 해킹. 그렇지 않으면, unutbu의 대답을 시도하십시오.

관련 문제