深度剖析使用python抓取网页正文的源码


Posted in Python onJune 11, 2014

本方法是基于文本密度的方法,最初的想法来源于哈工大的《基于行块分布函数的通用网页正文抽取算法》,本文基于此进行一些小修改。

约定:
       本文基于网页的不同行来进行统计,因此,假设网页内容是没有经过压缩的,就是网页有正常的换行的。

       有些新闻网页,可能新闻的文本内容比较短,但其中嵌入一个视频文件,因此,我会给予视频较高的权重;这同样适用于图片,这里有一个不足,应该是要根据图片显示的大小来决定权重的,但本文的方法未能实现这一点。

       由于广告,导航这些非正文内容通常以超链接的方式出现,因此文本将给予超链接的文本权重为零。

       这里假设正文的内容是连续的,中间不包含非正文的内容,因此实际上,提取正文内容,就是找出正文内容的开始和结束的位置。     

步骤:

       首先清除网页中CSS,Javascript,注释,Meta,Ins这些标签里面的内容,清除空白行。

       计算每一个行的经过处理的数值(1)

       计算上面得出的每行文本数的最大正子串的开始结束位置

其中第二步需要说明一下:

       对于每一行,我们需要计算一个数值,这个数值的计算如下:

              一个图片标签img,相当于出现长度为50字符的文本 (给予的权重),x1,

              一个视频标签embed,相当于出现长度为1000字符的文本, x2

              一行内所有链接的标签 a 的文本长度 x3 ,

              其他标签的文本长度 x4

              每行的数值 = 50 * x1其出现次数 + 1000 * x2其出现次数 + x4 ? 8

        //说明, -8 因为我们要计算一个最大正子串,因此要减去一个正数,至于这个数应该多大,我想还是按经验来吧。

完整代码

#coding:utf-8
import re
def remove_js_css (content):
    """ remove the the javascript and the stylesheet and the comment content (<script>....</script> and <style>....</style> <!-- xxx -->) """
    r = re.compile(r'''<script.*?</script>''',re.I|re.M|re.S)
    s = r.sub ('',content)
    r = re.compile(r'''<style.*?</style>''',re.I|re.M|re.S)
    s = r.sub ('', s)
    r = re.compile(r'''<!--.*?-->''', re.I|re.M|re.S)
    s = r.sub('',s)
    r = re.compile(r'''<meta.*?>''', re.I|re.M|re.S)
    s = r.sub('',s)
    r = re.compile(r'''<ins.*?</ins>''', re.I|re.M|re.S)
    s = r.sub('',s)
    return s
def remove_empty_line (content):
    """remove multi space """
    r = re.compile(r'''^\s+$''', re.M|re.S)
    s = r.sub ('', content)
    r = re.compile(r'''\n+''',re.M|re.S)
    s = r.sub('\n',s)
    return s
def remove_any_tag (s):
    s = re.sub(r'''<[^>]+>''','',s)
    return s.strip()
def remove_any_tag_but_a (s):
    text = re.findall (r'''<a[^r][^>]*>(.*?)</a>''',s,re.I|re.S|re.S)
    text_b = remove_any_tag (s)
    return len(''.join(text)),len(text_b)
def remove_image (s,n=50):
    image = 'a' * n
    r = re.compile (r'''<img.*?>''',re.I|re.M|re.S)
    s = r.sub(image,s)
    return s
def remove_video (s,n=1000):
    video = 'a' * n
    r = re.compile (r'''<embed.*?>''',re.I|re.M|re.S)
    s = r.sub(video,s)
    return s
def sum_max (values):
    cur_max = values[0]
    glo_max = -999999
    left,right = 0,0
    for index,value in enumerate (values):
        cur_max += value
        if (cur_max > glo_max) :
            glo_max = cur_max
            right = index
        elif (cur_max < 0):
            cur_max = 0
    for i in range(right, -1, -1):
        glo_max -= values[i]
        if abs(glo_max < 0.00001):
            left = i
            break
    return left,right+1
def method_1 (content, k=1):
    if not content:
        return None,None,None,None
    tmp = content.split('\n')
    group_value = []
    for i in range(0,len(tmp),k):
        group = '\n'.join(tmp[i:i+k])
        group = remove_image (group)
        group = remove_video (group)
        text_a,text_b= remove_any_tag_but_a (group)
        temp = (text_b - text_a) - 8 
        group_value.append (temp)
    left,right = sum_max (group_value)
    return left,right, len('\n'.join(tmp[:left])), len ('\n'.join(tmp[:right]))
def extract (content):
    content = remove_empty_line(remove_js_css(content))
    left,right,x,y = method_1 (content)
    return '\n'.join(content.split('\n')[left:right])

代码 从最后一个函数开始调用。

Python 相关文章推荐
Python写的创建文件夹自定义函数mkdir()
Aug 25 Python
python入门教程之识别验证码
Mar 04 Python
python访问抓取网页常用命令总结
Apr 11 Python
Python实现的快速排序算法详解
Aug 01 Python
django在接受post请求时显示403forbidden实例解析
Jan 25 Python
用Python实现数据的透视表的方法
Nov 16 Python
python 中pyqt5 树节点点击实现多窗口切换问题
Jul 04 Python
详解Python中的正斜杠与反斜杠
Aug 09 Python
Python 变量的创建过程详解
Sep 02 Python
python实现输入任意一个大写字母生成金字塔的示例
Oct 27 Python
python实现12306登录并保存cookie的方法示例
Dec 17 Python
如何在sublime编辑器中安装python
May 20 Python
python k-近邻算法实例分享
Jun 11 #Python
浅析python 内置字符串处理函数的使用方法
Jun 11 #Python
python使用正则表达式检测密码强度源码分享
Jun 11 #Python
Python查看多台服务器进程的脚本分享
Jun 11 #Python
Python SQLite3数据库操作类分享
Jun 10 #Python
Python不规范的日期字符串处理类
Jun 10 #Python
Python ORM框架SQLAlchemy学习笔记之数据查询实例
Jun 10 #Python
You might like
『PHP』PHP截断函数mb_substr()使用介绍
2013/04/22 PHP
php使用sql数据库 获取字段问题介绍
2013/08/12 PHP
PHP上传图片进行等比缩放可增加水印功能
2014/01/13 PHP
PHP基于自定义函数生成笛卡尔积的方法示例
2017/09/30 PHP
PHP设计模式之注册树模式分析
2018/01/26 PHP
PHP实现的无限分类类库定义与用法示例【基于thinkPHP】
2018/08/06 PHP
PHP 命名空间和自动加载原理与用法实例分析
2020/04/29 PHP
Javascript开发包大全整理
2006/12/22 Javascript
showModelDialog弹出文件下载窗口的使用示例
2013/11/19 Javascript
教你如何在 Javascript 文件里使用 .Net MVC Razor 语法
2014/07/23 Javascript
JavaScript极简入门教程(二):对象和函数
2014/10/25 Javascript
javascript实现自动填写表单实例简析
2015/12/02 Javascript
原生javascript AJAX 三级联动的实现代码
2018/05/04 Javascript
在react中使用vuex的示例代码
2018/07/30 Javascript
[46:10]2014 DOTA2国际邀请赛中国区预选赛 CnB VS HGT
2014/05/21 DOTA
Python实现拼接多张图片的方法
2014/12/01 Python
Python使用matplotlib和pandas实现的画图操作【经典示例】
2018/06/13 Python
python定向爬虫校园论坛帖子信息
2018/07/23 Python
Python使用psutil获取进程信息的例子
2019/12/17 Python
使用TensorFlow直接获取处理MNIST数据方式
2020/02/10 Python
tensorflow模型文件(ckpt)转pb文件的方法(不知道输出节点名)
2020/04/22 Python
python 使用raw socket进行TCP SYN扫描实例
2020/05/05 Python
套娃式文件夹如何通过Python批量处理
2020/08/23 Python
详解HTML5中的标签
2015/06/19 HTML / CSS
一个不错的HTML5 Canvas多层点击事件监听实例
2014/04/29 HTML / CSS
课堂教学改革实施方案
2014/03/17 职场文书
商务英语广告词大全
2014/03/18 职场文书
弘扬民族精神演讲稿
2014/05/07 职场文书
禁毒宣传标语
2014/06/19 职场文书
毕业实习自我鉴定范文2014
2014/09/26 职场文书
大学毕业典礼致辞
2015/07/29 职场文书
六年级语文教学反思
2016/03/03 职场文书
2016年大学生社区服务活动总结
2016/04/06 职场文书
HTML+CSS制作心跳特效的实现
2021/05/26 HTML / CSS
Java如何实现树的同构?
2021/06/22 Java/Android
Nginx 路由转发和反向代理location配置实现
2021/11/11 Servers