Python常用的爬虫技巧总结


Posted in Python onMarch 28, 2016

用python也差不多一年多了,python应用最多的场景还是web快速开发、爬虫、自动化运维:写过简单网站、写过自动发帖脚本、写过收发邮件脚本、写过简单验证码识别脚本。

爬虫在开发过程中也有很多复用的过程,这里总结一下,以后也能省些事情。

1、基本抓取网页

get方法

import urllib2
 
url = "http://www.baidu.com"
response = urllib2.urlopen(url)
print response.read()

post方法

import urllib
import urllib2
 
url = "http://abcde.com"
form = {'name':'abc','password':'1234'}
form_data = urllib.urlencode(form)
request = urllib2.Request(url,form_data)
response = urllib2.urlopen(request)
print response.read()

2、使用代理IP

    在开发爬虫过程中经常会遇到IP被封掉的情况,这时就需要用到代理IP;

在urllib2包中有ProxyHandler类,通过此类可以设置代理访问网页,如下代码片段:

import urllib2
 
proxy = urllib2.ProxyHandler({'http': '127.0.0.1:8087'})
opener = urllib2.build_opener(proxy)
urllib2.install_opener(opener)
response = urllib2.urlopen('http://www.baidu.com')
print response.read()

3、Cookies处理

    cookies是某些网站为了辨别用户身份、进行session跟踪而储存在用户本地终端上的数据(通常经过加密),python提供了cookielib模块用于处理cookies,cookielib模块的主要作用是提供可存储cookie的对象,以便于与urllib2模块配合使用来访问Internet资源.

代码片段:

import urllib2, cookielib
 
cookie_support= urllib2.HTTPCookieProcessor(cookielib.CookieJar())
opener = urllib2.build_opener(cookie_support)
urllib2.install_opener(opener)
content = urllib2.urlopen('http://XXXX').read()

    关键在于CookieJar(),它用于管理HTTP cookie值、存储HTTP请求生成的cookie、向传出的HTTP请求添加cookie的对象。整个cookie都存储在内存中,对CookieJar实例进行垃圾回收后cookie也将丢失,所有过程都不需要单独去操作。

  手动添加cookie

cookie = "PHPSESSID=91rurfqm2329bopnosfu4fvmu7; 
kmsign=55d2c12c9b1e3; 
KMUID=b6Ejc1XSwPq9o756AxnBAg="
request.add_header("Cookie", cookie)

4、伪装成浏览器

    某些网站反感爬虫的到访,于是对爬虫一律拒绝请求。所以用urllib2直接访问网站经常会出现HTTP Error 403: Forbidden的情况

对有些 header 要特别留意,Server 端会针对这些 header 做检查

  1.User-Agent 有些 Server 或 Proxy 会检查该值,用来判断是否是浏览器发起的 Request

  2.Content-Type 在使用 REST 接口时,Server 会检查该值,用来确定 HTTP Body 中的内容该怎样解析。

这时可以通过修改http包中的header来实现,代码片段如下:

import urllib2
 
headers = {
  'User-Agent':'Mozilla/5.0 (Windows; U; Windows NT 6.1; en-US; rv:1.9.1.6) Gecko/20091201 Firefox/3.5.6'
}
request = urllib2.Request(
  url = 'http://my.oschina.net/jhao104/blog?catalog=3463517',
  headers = headers
)
print urllib2.urlopen(request).read()

5、页面解析

    对于页面解析最强大的当然是正则表达式,这个对于不同网站不同的使用者都不一样,就不用过多的说明,附两个比较好的网址:

正则表达式入门:https://3water.com/article/18526.htm

正则表达式在线测试:http://tools.3water.com/regex/javascript

其次就是解析库了,常用的有两个lxml和BeautifulSoup,对于这两个的使用介绍两个比较好的网站:

lxml:https://3water.com/article/67125.htm

BeautifulSoup:https://3water.com/article/43572.htm

对于这两个库,我的评价是,都是HTML/XML的处理库,Beautifulsoup纯python实现,效率低,但是功能实用,比如能用通过结果搜索获得某个HTML节点的源码;lxmlC语言编码,高效,支持Xpath

6、验证码的处理

对于一些简单的验证码,可以进行简单的识别。本人也只进行过一些简单的验证码识别。但是有些反人类的验证码,比如12306,可以通过打码平台进行人工打码,当然这是要付费的。

7、gzip压缩

    有没有遇到过某些网页,不论怎么转码都是一团乱码。哈哈,那说明你还不知道许多web服务具有发送压缩数据的能力,这可以将网络线路上传输的大量数据消减 60% 以上。这尤其适用于 XML web 服务,因为 XML 数据 的压缩率可以很高。

但是一般服务器不会为你发送压缩数据,除非你告诉服务器你可以处理压缩数据。

于是需要这样修改代码:

import urllib2, httplib
request = urllib2.Request('http://xxxx.com')
request.add_header('Accept-encoding', 'gzip')    1
opener = urllib2.build_opener()
f = opener.open(request)

这是关键:创建Request对象,添加一个 Accept-encoding 头信息告诉服务器你能接受 gzip 压缩数据

然后就是解压缩数据:

import StringIO
import gzip
 
compresseddata = f.read() 
compressedstream = StringIO.StringIO(compresseddata)
gzipper = gzip.GzipFile(fileobj=compressedstream) 
print gzipper.read()

8、多线程并发抓取

    单线程太慢的话,就需要多线程了,这里给个简单的线程池模板 这个程序只是简单地打印了1-10,但是可以看出是并发的。

虽然说python的多线程很鸡肋,但是对于爬虫这种网络频繁型,还是能一定程度提高效率的。

from threading import Thread
from Queue import Queue
from time import sleep
# q是任务队列
#NUM是并发线程总数
#JOBS是有多少任务
q = Queue()
NUM = 2
JOBS = 10
#具体的处理函数,负责处理单个任务
def do_somthing_using(arguments):
  print arguments
#这个是工作进程,负责不断从队列取数据并处理
def working():
  while True:
    arguments = q.get()
    do_somthing_using(arguments)
    sleep(1)
    q.task_done()
#fork NUM个线程等待队列
for i in range(NUM):
  t = Thread(target=working)
  t.setDaemon(True)
  t.start()
#把JOBS排入队列
for i in range(JOBS):
  q.put(i)
#等待所有JOBS完成
q.join()
Python 相关文章推荐
Python模块学习 re 正则表达式
May 19 Python
Python中获取网页状态码的两个方法
Nov 03 Python
对python遍历文件夹中的所有jpg文件的实例详解
Dec 08 Python
使用pyinstaller打包PyQt4程序遇到的问题及解决方法
Jun 24 Python
Python 实用技巧之利用Shell通配符做字符串匹配
Aug 23 Python
学python安装的软件总结
Oct 12 Python
Python全局锁中如何合理运用多线程(多进程)
Nov 06 Python
python模拟点击网页按钮实现方法
Feb 25 Python
python实现横向拼接图片
Mar 23 Python
Python中使用threading.Event协调线程的运行详解
May 02 Python
解决pycharm导入numpy包的和使用时报错:RuntimeError: The current Numpy installation (‘D:\\python3.6\\lib\\site-packa的问题
Dec 08 Python
pycharm远程连接服务器并配置python interpreter的方法
Dec 23 Python
Python对数据库操作
Mar 28 #Python
Python字符串切片操作知识详解
Mar 28 #Python
python Django框架实现自定义表单提交
Mar 25 #Python
python Django批量导入数据
Mar 25 #Python
python Django批量导入不重复数据
Mar 25 #Python
用Python实现斐波那契(Fibonacci)函数
Mar 25 #Python
Python基础教程之正则表达式基本语法以及re模块
Mar 25 #Python
You might like
PHP闭包函数详解
2016/02/13 PHP
Thinkphp框架开发移动端接口(1)
2016/08/18 PHP
php+js实现裁剪任意形状图片
2018/10/31 PHP
PHP中Session ID的实现原理实例分析
2019/08/17 PHP
发一个自己用JS写的实用看图工具实现代码
2008/07/26 Javascript
PHP 与 js的通信(via ajax,json)
2010/11/16 Javascript
javascript设置金额样式转换保留两位小数示例代码
2013/12/04 Javascript
jQuery中empty()方法用法实例
2015/01/16 Javascript
jQuery实现智能判断固定导航条或侧边栏的方法
2016/09/04 Javascript
jquery插件ContextMenu设置右键菜单
2017/03/13 Javascript
bootstrap动态添加面包屑(breadcrumb)及其响应事件的方法
2017/05/25 Javascript
利用node实现一个批量重命名文件的函数
2017/12/21 Javascript
js中split()方法得到的数组长度问题
2018/07/19 Javascript
layui radio性别单选框赋值方法
2018/08/15 Javascript
[00:52]DOTA2齐天大圣预告片
2016/08/13 DOTA
[02:58]魔廷新尊——痛苦女王至宝语音台词节选
2020/06/14 DOTA
详解python eval函数的妙用
2017/11/16 Python
Python 获取中文字拼音首个字母的方法
2018/11/28 Python
python3.6+django2.0+mysql搭建网站过程详解
2019/07/24 Python
MATLAB数学建模之画图汇总
2020/07/16 Python
canvas使用注意点总结
2013/07/19 HTML / CSS
深入解析HTML5中的Blob对象的使用
2015/09/08 HTML / CSS
HTML5的Video标签有部分MP4无法播放的问题解析(多图)
2017/08/18 HTML / CSS
HTML5 Blob 实现文件下载功能的示例代码
2019/11/29 HTML / CSS
印尼第一大家居、生活和家具电子商务:Ruparupa
2019/11/25 全球购物
Jacques Lemans德国:奥地利钟表品牌
2019/12/26 全球购物
Java TransactionAPI (JTA) 主要包含几部分
2012/12/07 面试题
面试后的英文感谢信
2014/02/01 职场文书
教师试用期自我鉴定
2014/02/12 职场文书
放飞梦想演讲稿200字
2014/08/26 职场文书
2014市国税局对照检查材料思想汇报
2014/09/23 职场文书
2014年小学教师工作总结
2014/11/10 职场文书
小学生暑假生活总结
2015/07/13 职场文书
《当代神农氏》教学反思
2016/02/23 职场文书
光之国的四大叛徒:第一贝利亚导致宇宙毁灭,赛文奥特曼在榜
2022/03/18 日漫
nginx日志格式分析和修改
2022/04/28 Servers