基于request的爬虫练习
引言
概述
概念:基于网络请求的模块
作用:用来模拟浏览器发请求,从而实现爬虫
通用爬虫
步骤:
- 指定url
- 请求发送:get返回的是一个响应对象
- 获取响应数据: text返回的是字符串形式的响应数据
- 持久化存储
爬取搜狗首页的页面源码数据
1 |
import requests |
实现一个简易的网页采集器
- 请求参数动态化(自定义字典给get方法的params传参)
- 使用UA伪装
1 |
url = 'https://www.sogou.com/web' |
动态加载的数据
- 页面中想要爬取的内容并不是请求当前url得到的,而是通过另一个网络请求请求到的数据(例如,滚轮滑到底部,会发送ajax,对局部进行刷新)
例子:爬取豆瓣电影中动态加载出的电影详情
我们想爬取的页面是:豆瓣电影分类排行榜 - 科幻片 https://movie.douban.com/typerank?type_name=%E7%A7%91%E5%B9%BB&type=17&interval_id=100:90&action=
首先在chorme的抓包工具中进行全局搜索发现它不是请求当前url得到的,而是一个新的url:
https://movie.douban.com/j/chart/top_list?当然这是一个ajax请求(在chorme的抓包工具中选择 XHR 可以进行查看)
在寻找另一部电影,请求的url仍然是
https://movie.douban.com/j/chart/top_list?然后我们就需要找参数的规律了:
1
2
3
4
5
6
7
8
9
10
11type: 17
interval_id: 100:90
action:
start: 0
limit: 1
# 第二部
type: 17
interval_id: 100:90
action:
start: 20
limit: 20start 和 limit 是可以变化的,基于例二,我们自定义字典进行传参,然后进行尝试。
1 |
url = 'https://movie.douban.com/j/chart/top_list' |
note:response.json() 可以免除我们手动使用json进行loads的过程。
爬取肯德基的餐厅位置信息
地址为:
http://www.kfc.com.cn/kfccda/storelist/index.aspxpost请求
一次爬取多页数据
思路:
- 首先,数据是动态加载的,分析请求方式为 post 发出的 url 与 data。
- 通过pageSize就可以在循环内完成多所有地址的爬取。
1 |
url = 'http://www.kfc.com.cn/kfccda/ashx/GetStoreList.ashx?op=keyword' |
补充:可以使用代理服务器,如搜索:全网代理IP
中标公告提取
- 需求
https://www.fjggfw.gov.cn/Website/JYXXNew.aspx 福建省公共资源交易中心
提取内容:
工程建设中的中标结果信息/中标候选人信息
完整的html中标信息
第一中标候选人
中标金额
中标时间
其它参与投标的公司
思路:
- 从首页打开一个公告,先尝试得到一个公告的信息。
- 在得到另一个公告的信息进行比较,只有ID是变化的,所以有了ID就可以批量爬取了。
- 回到首页,判断加载方式,确定数据的请求方式,url以及参数。
实现过程:
- 确认爬取的数据都是动态加载出来的
- 在首页中捕获到ajax请求对应的数据包,从该数据包中提取出请求的url和请求参数
- 对提取到的url进行请求发送,获取响应数据(json),(包含ID信息)
- 从json串中提取到每一个公告对应的id值
- 将id值和中标信息对应的url进行整合,进行请求发送捕获到每一个公告对应的中标信息数据
1 |
# 该部分为得到一个公告的信息,但是我们这里的ID不灵活,需要进一步改进。 |
完成了对公告详情的爬取后,接下来批量爬取公告。
1 |
# 该部分完成了对前5页的公告信息进行爬取 |
爬取图片
如何做?
- 基于requests
- 基于urllib
- 区别:urllib中的 urlretrieve 不可以进行UA伪装
requests在urllib基础上产生,更加pythonic!
基于requests的图片爬取
1 |
import requests |
- request更具通用性,数据可以展示为:text(字符串),json(列表/字典),content(字节)。
基于urllib的图片爬取
1 |
# 基于urllib |
- 由于urlretrieve不能做UA伪装,所以存在图片缺失的可能。
聚焦爬虫
较通用爬虫相比,增加了数据解析。
数据解析
概念:将一整张页面的局部数据进行提取/解析
作用:用来实现聚焦爬虫
实现方式:
- 正则
- bs4
- xpath
- pyquery
数据解析的通用原理是什么?
- 标签的定位
- 数据的提取
页面中的相关的字符串的数据都存储在哪里?
- 标签中间
- 标签的属性中
基于聚焦爬虫的编码流程
- 指定url
- 发起请求
- 获取响应数据
- 数据解析
- 持久化存储
正则解析
爬取煎蛋网中的图片
- 地址为:
http://jandan.net/pic/MjAxOTEwMDktNjk=#comments
实现过程:
- 指定url
- 获取响应数据
- 数据解析
- 写正则表达式
- 正则匹配
- 持久化存储
1 |
import re |
note:内容依据响应数据page_text,而不是根据浏览器中网页上的代码,上面就出现一个字母的大小写不同而导致正则失效的例子。
bs4解析
环境的安装:
- pip install bs4
- pip install lxml
bs4的解析原理:
- 实例化一个BeatifulSoup的一个对象,把即将被解析的页面源码数据加载到该对象中
- 需要调用BeatifulSoup对象中的相关的方法和属性进行标签定位和数据的提取
BeatifulSoup的实例化
- BeatifulSoup(fp, ‘lxml’) 将本地存储的html文档中的页面源码数据加载到该对象中
- BeatifulSoup(page_text, ‘lxml’) 将从互联网中请求到的页面源码数据加载到该对象中
标签的定位
soup.tagName: 只可以定位到第一个tagName标签
属性定位:
- soup.find(‘div’,’attrName=’value’) 只能定位到符合要求的第一个
- soup.findAll:返回列表,可以定位到符合要求的所有标签
note:只有class需要加下划线,其它直接用原名就可以。
选择器定位:
- select(‘选择器’)
- 选择器:id,class,tag,层级选择器(大于号表示一个层级,空格表示多个层级)
取文本
- text:将标签中所有文本取出
- string:将标签中直系的文本取出
取属性
- tag[‘attrName’]
熟悉
此为练手的html。
1 |
<html lang="en"> |
熟悉 BeautifulSoup 的选择器以及如何取文本和属性
1 |
fp = open('./test.html',encoding='utf-8')
|
爬取三国演义小说的标题和内容
- 地址为:
http://www.shicimingju.com/book/sanguoyanyi.html
数据解析流程:
- 首先定位标签
- 然后取出文本和内容
1 |
main_url = 'http://www.shicimingju.com/book/sanguoyanyi.html' |
xpath 解析
环境的安装
- pip install lxml
解析原理
- 实例化一个etree的对象,且把即将被解析的页面源码数据加载到该对象中
- 调用etree对象中的xpath方法结合着不同形式的xpath表达式进行标签定位和数据提取
etree对象的实例化
- etree.parse(‘fileName’)
- etree.HTML(page_text)
标签定位
- 最左侧的/:一定要从根标签开始进行标签定位
- 非最左侧的/:表示一个层级
- 最左侧的//:可以从任意位置进行指定标签的定位
- 非最左侧的//:表示多个层级
- 属性定位:
- //tagName[@attrName=”value”]
- 索引定位:
- //tagName[@attrName=”value”]/li[2],索引是从1开始的
- 逻辑运算:
- 找到href属性值为空且class属性值为du的a标签- //a[@href=”” and @class=”du”]
- 模糊匹配:
- //div[contains(@class, “ng”)]
- //div[starts-with(@class, “ta”)]
取文本
- /text():取直系的文本内容
- //text():取所有文本内容
取属性
- /@attrName
note:
- 返回的都是列表
- 在google中的Element可以直接copy xpath
熟悉
依旧使用上面的html练手
1 |
from lxml import etree |
爬取虎牙主播名称,热度和标题
1 |
url = 'https://www.huya.com/g/xingxiu' |
爬取所有页码的妹子
地址为:http://pic.netbian.com/4kmeinv/
- 涉及中文乱码
- 以前对response的 encoding 这样代价大
iso-8859-1 –> utf-8 先编码成iso-8859-1 在解码成 utf或gbk
- 以前对response的 encoding 这样代价大
- 多页码数据的爬取
- 制定一个通用的url模板
基于request的爬虫练习的更多相关文章
- 基于golang分布式爬虫系统的架构体系v1.0
基于golang分布式爬虫系统的架构体系v1.0 一.什么是分布式系统 分布式系统是一个硬件或软件组件分布在不同的网络计算机上,彼此之间仅仅通过消息传递进行通信和协调的系统.简单来说就是一群独立计算机 ...
- 爬虫,基于request,bs4 的简单实例整合
简单爬虫示例 爬取抽屉,以及自动登陆抽屉点赞 先查看首页拿到cookie,然后登陆要携带首页拿到的 cookie 才可以通过验证 """""" ...
- 爬虫学习之基于Scrapy的爬虫自动登录
###概述 在前面两篇(爬虫学习之基于Scrapy的网络爬虫和爬虫学习之简单的网络爬虫)文章中我们通过两个实际的案例,采用不同的方式进行了内容提取.我们对网络爬虫有了一个比较初级的认识,只要发起请求获 ...
- 基于 Electron 的爬虫框架 Nightmare
作者:William 本文为原创文章,转载请注明作者及出处 Electron 可以让你使用纯 JavaScript 调用 Chrome 丰富的原生的接口来创造桌面应用.你可以把它看作一个专注于桌面应用 ...
- 基于Nodejs的爬虫
简介 基于 Node.JS 爬取 博客园 1W+博文,对博文内容做关键词提取,生成词云. 演示 安装 安装 git.Node.JS.MongoDB.Yarn 克隆代码 git clone git@gi ...
- 基于python的爬虫(一)
抓取网页 python核心库 urllib2 实现对静态网页的抓取,不得不说,"人生苦短,我用python"这句话还是有道理的,要是用java来写,这估计得20行代码 (对不住了博 ...
- 基于.net的爬虫应用-DotnetSpider
最近应朋友的邀请,帮忙做了个简单的爬虫程序,要求不高,主要是方便对不同网站的爬取进行扩展,获取到想要的数据信息即可.当然,基于数据的后期分析功能是后话,以后的随笔我会逐步的介绍. 开源的爬虫框架比较多 ...
- 基于scrapy-redis分布式爬虫的部署
redis分布式部署 1.scrapy框架是否可以自己实现分布式? - 不可以.原因有二. 其一:因为多台机器上部署的scrapy会各自拥有各自的调度器,这样就使得多台机器无法分配start_urls ...
- 基于scrapy-redis分布式爬虫(简易)
redis分布式部署 1.scrapy框架是否可以自己实现分布式? - 不可以.原因有二. 其一:因为多台机器上部署的scrapy会各自拥有各自的调度器,这样就使得多台机器无法分配start_urls ...
随机推荐
- 4'.deploy.prototxt
1: 神经网络中,我们通过最小化神经网络来训练网络,所以在训练时最后一层是损失函数层(LOSS), 在测试时我们通过准确率来评价该网络的优劣,因此最后一层是准确率层(ACCURACY). 但是当我们真 ...
- linux基础_vi和vim快捷键
(1)拷贝当前行 yy,拷贝当前行向下5行 5yy,并粘贴. (2)删除当前行 dd, 删除当前行向下的5行 5dd. (3)在文件中查找某个单词.[在命令行下使用 /+关键字,回车查找,输入n就是查 ...
- 【转载】解决繁体、日文游戏乱码的五种方法 转载自:http://tieba.baidu.com/p/488627981
方法1:转换区域 开始——设置——控制面板——区域和语言选项——分别选择“高级”和“区域选项”标签——在其下拉框中都选择“日语”(或“日本”)(选项有点多,慢慢找)——重启后即可生效. *某影注:日语 ...
- [MySQL优化] -- 如何了解SQL的执行频率
MySQL 客户端连接成功后,通过 show [session|global]status 命令 可以提供服务器状态信息,也可以在操作系统上使用 mysqladmin extended-status ...
- 串口+RS485驱动
其实RS485不算什么协议,只是物理层做了差分传输,AB两线的电压差来表示0,1,0,1,可靠性和距离更加好,因此,一个串口外设只能作为半双工使用,而RS232是可以全双工的. max485模块可以直 ...
- Unity 连接WebSocket(ws://)服务器
Unity 连接ws,不用任何插件,忙活了一天终于搞定了,一直连接不上,原来是没有添加header, 代码比较简单,直接贴出来普度众生 using System; using System.Net.W ...
- 自己编写一个Java监听器
Java监听器 1.原理: 当范围对象的状态发生变化的时候,服务器自动调用监听器对象中的方法. 例如:创建一个“人”类Class Person 人拥有吃的方法public void eat(){},我 ...
- $ python manage.py makemigrations You are trying to add a non-nullable field 'name' to course without a default; we can't do that (the database needs something to populate existing rows). Please selec
问题: $ python manage.py makemigrationsYou are trying to add a non-nullable field 'name' to course wit ...
- java实现上传文件夹
我们平时经常做的是上传文件,上传文件夹与上传文件类似,但也有一些不同之处,这次做了上传文件夹就记录下以备后用. 首先我们需要了解的是上传文件三要素: 1.表单提交方式:post (get方式提交有大小 ...
- Win7下使用Visual Studio为WinXP编译可执行文件
造冰箱的大熊猫@cnblogs 2019/8/5 2019/9/5补充:参见这里 1.问题 开发机是64位Win7,想开发能够运行在WinXP下的C程序,怎么办? 2.解决方法 一个简单粗暴的解决办法 ...