昊天SEO

python 正则表达式过滤文本中的html标签 源代码解析

#py2.7
#coding:utf-8
import re
import os
import chardet
def filter_tag(htmlstr):
 re_cdata = re.compile('<!DOCTYPE HTML PUBLIC[^>]*>', re.I)
 re_script = re.compile('<\s*script[^>]*>[^<]*<\s*/\s*script\s*>', re.I) #过滤脚本
 re_style = re.compile('<\s*style[^>]*>[^<]*<\s*/\s*style\s*>', re.I) #过滤style
 re_br = re.compile('<br\s*?/?>')
 re_h = re.compile('</?\w+[^>]*>')
 re_comment = re.compile('<!--[\s\S]*-->')
 s = re_cdata.sub('', htmlstr)
 s = re_script.sub('', s)
 s=re_style.sub('',s)
 s=re_br.sub('\n',s)
 s=re_h.sub(' ',s)
 s=re_comment.sub('',s)
 blank_line=re.compile('\n+')
 s=blank_line.sub('\n',s)
 s=re.sub('\s+',' ',s)
 s=replaceCharEntity(s)
 return s
def replaceCharEntity(htmlstr):
 CHAR_ENTITIES={'nbsp':'','160':'',
 'lt':'<','60':'<',
 'gt':'>','62':'>',
 'amp':'&','38':'&',
 'quot':'"','34':'"'}
 re_charEntity=re.compile(r'&#?(?P<name>\w+);') #命名组,把 匹配字段中\w+的部分命名为name,可以用group函数获取
 sz=re_charEntity.search(htmlstr)
 while sz:
 #entity=sz.group()
 key=sz.group('name') #命名组的获取
 try:
 htmlstr=re_charEntity.sub(CHAR_ENTITIES[key],htmlstr,1) #1表示替换第一个匹配
 sz=re_charEntity.search(htmlstr)
 except KeyError:
 htmlstr=re_charEntity.sub('',htmlstr,1)
 sz=re_charEntity.search(htmlstr)
 return htmlstr
if __name__=='__main__':
 cpath=os.getcwd()
 
 for root,dirs,files in os.walk(cpath):
 for file in files:
 if file.endswith('htm') or file.endswith('html'):
 f=open(root+os.path.sep+file)
 stream=f.read()
 htmlstr =stream.decode(chardet.detect(stream)['encoding'])
 rs=filter_tag(htmlstr)
 f.close()
 txtname=re.sub(r'.htm*$','.txt',file)
 print txtname
 f=open(root+os.path.sep+txtname,'w')
 f.write(rs.encode('utf-8'))
 f.close()

总结:

转义符:

. 匹配除换行符以外的任意字符

\w 匹配字母或数字或下划线或汉字

\s 匹配任意的空白符

\d 匹配数字

\b 匹配单词的开始或结束

^ 匹配字符串的开始

$ 匹配字符串的结束

\W 匹配任意不是字母,数字,下划线,汉字的字符

\S 匹配任意不是空白符的字符

\D 匹配任意非数字的字符

\B 匹配不是单词开头或结束的位置

[^x] 匹配除了x以外的任意字符

[^aeiou] 匹配除了aeiou这几个字母以外的任意字符

常用的限定符代码/语法说明:

*重复零次或更多次

+重复一次或更多次

?重复零次或一次

{n}重复n次

{n,}重复n次或更多次

{n,m}重复n到m次

关于命名组:

命名组:(?P<name>…..),详见:http://scm002.iteye.com/blog/1491521

这篇文章里面还提到了界定( 问号开头,前向则有个'<‘号,非则有个’!’ 号 ):

前向界定 (?<=…)

后向界定 (?=…)

前向非界定 (?<!….)

后向非界定 (?!…..)

网站的维护离不开大家的支持鼓励,捐赠让我更有动力走的更远&& 也可以关注我的微信公众号,发布更多的干货
本文网址:https://www.168seo.cn/python/1190.html

评论 抢沙发

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址