网页视频抓取脚本(什么是爬虫?实践来源于理论,做爬虫前肯定要先了解相关的规则和原理)
优采云 发布时间: 2022-01-14 10:19网页视频抓取脚本(什么是爬虫?实践来源于理论,做爬虫前肯定要先了解相关的规则和原理)
什么是爬行动物?
实践源于理论,成为爬虫前必须了解相关规则和原则。
首先我们来看看爬虫的定义:网络爬虫(也被称为网络蜘蛛,网络机器人,在FOAF社区,更常被称为网页追逐者),是一种自动爬取万维网按照一定的规则。信息程序或脚本。总之,它是在线信息搬运工。
我们来看看爬虫应该遵循的规则:robots 协议是一个 ASCII 编码的文本文件,存放在 网站 根目录下,它通常告诉网络搜索引擎的 bot(也称为网络蜘蛛)这个 < @网站 @网站 中的哪些内容不应该被搜索引擎机器人检索,哪些可以被机器人检索。一句话,告诉你什么可以爬,什么不能爬。
了解了定义和规则后,终于熟悉了爬虫的基本原理。这很简单。作为一个灵魂画师,我画个*敏*感*词*给你看,你就明白了。
(⊙o⊙)… 不好意思,鼠标写的这么难看,不好意思说学了书法,脸上的字都在呱呱叫。
项目背景
理论部分基本讲完了。有的小朋友觉得我太啰嗦了,废话不多说,直接说实操部分吧。本次爬虫小项目是应朋友的需求,对中国木材价格指数网的红木价格数据进行爬取,方便红木研报的撰写。网站像这样:
必填字段已用红色框标记。粗略看一下数据量,1751页有5万多条记录。如果你尝试复制粘贴,你不会知道它会被粘贴到猴年。而python只运行了几分钟,就将所有数据保存到你的excel中,是不是很舒服?\
项目实战
工具:PyCharm
Python 版本:Python 3.7
浏览器:Chrome(推荐)
第一次写爬虫的朋友可能会觉得很麻烦。我们不要惊慌。让我们先尝试爬上一页数据。
一次抓取一页
首先我们需要简单分析一下网页的结构,右键查看,然后点击Network,刷新网页,继续点击Name列表中的第一个。我们发现这个网站的请求方式是GET,请求头headers反映了用户的计算机系统、浏览器版本等信息。
然后,pip install 并导入爬虫所需的所有库,并注释所有库的功能。
import csv #用于把爬取的数据存储为csv格式,可以excel直接打开的
import time #用于对请求加延时,爬取速度太快容易被反爬
from time import sleep #同上
import random #用于对延时设置随机数,尽量模拟人的行为
import requests #用于向网站发送请求
from lxml import etree #lxml为第三方网页解析库,强大且速度快
构造请求url,添加header信息headers复制上面标注的User-Agent,通过requests.get方法向服务器发送请求,返回html文本。添加标头的目的是告诉服务器您是访问其网站 的真实人。如果不加headers直接访问服务器,会显示python正在其他服务器上访问,那么你很可能被反爬了。常见的反爬就是屏蔽你的ip。
url = 'http://yz.yuzhuprice.com:8003/findPriceByName.jspx?page.curPage=1&priceName=%E7%BA%A2%E6%9C%A8%E7%B1%BB'
headers = {
'User-Agent': "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/81.0.4044.129 Safari/537.36",
}
response = requests.get(url, headers=headers, timeout=10)
html = response.text
print(html)
让我们运行上面的代码,看看效果:
看到这里,第一次接触爬虫的朋友可能会有些疑惑。
其实这就是网页的源码,我们右键打开源码看看。
它看起来像这样:
而我们需要提取的数据隐藏在这个网页的源代码中。我们使用lxml库中的etree方法来解析网页。
parse = etree.HTML(html) #解析网页
解析之后,我们就可以愉快的提取出我们需要的数据了。方法很多,比如xpath、select、美汤、最难的re(正则表达式)。本文爬取的数据结构比较简单,直接玩xpath就行了。
我们在源码中发现每一行数据对应一个id=173200的tr,那么先把这些tr提取出来。
all_tr = parse.xpath('//*[@id="173200"]')
有些朋友不会写xpath。
然后找个简单的方法直接复制需要的xpath。
所有的trs都已经提取出来了,接下来还要从tr中依次提取具体的字段。例如,提取产品名称字段,点击第一个 tr,选择产品,并复制其 xpath。其他领域也是如此。
需要注意以下几点,tr={key1 : value1, key2 : value2 } 是python的字典数据类型(也可以根据自己的兴趣或需要保存为列表或元组类型)。''.join 表示将得到的列表转换成字符串。./表示继承前面的//*[@id="173200"],strip()表示对提取的数据进行简单的格式清理。
for tr in all_tr:
tr = {
'name': ''.join(tr.xpath('./td[1]/text()')).strip(),
'price': ''.join(tr.xpath('./td[2]/text()')).strip(),
'unit': ''.join(tr.xpath('./td[3]/text()')).strip(),
'supermaket': ''.join(tr.xpath('./td[4]/text()')).strip(),
'time': ''.join(tr.xpath('./td[5]/text()')).strip()
}
让我们打印 print(tr) 看看效果。
此时,你的心情可能是这样的:
不过还没完,有数据了,我们要把csv格式保存到本地,这一步比较简单,直接粘贴代码。
with open('wood.csv', 'a', encoding='utf_8_sig', newline='') as fp:
# 'a'为追加模式(添加)
# utf_8_sig格式导出csv不乱码
fieldnames = ['name', 'price', 'unit', 'supermaket', 'time']
writer = csv.DictWriter(fp, fieldnames)
writer.writerow(tr)
打开新生成的wood.csv,如下所示:
两个爬取多个页面
不要太高兴,你只是爬了一页数据,别人复制粘贴比你快。我们的野心不在这里,在诗和远方,哦不,是秒爬海量数据。
那么,我们如何爬取多页数据呢?没错,就是for循环。
我们回过头来分析一下url:
:8003/findPriceByName.jspx?page.curPage=1&priceName=%E7%BA%A2%E6%9C%A8%E7%B1%BB
我们试试把里面的page.curPage改成2,如下:
你可能会发现一个谜,只要改变page.curPage,就可以翻页。OK,那我们直接在url前面加个循环就好了。format(x) 是一个格式字符串函数,它接受无限数量的参数。
for x in range(1,3):
url = 'http://yz.yuzhuprice.com:8003/findPriceByName.jspx?page.curPage={}&priceName=%E7%BA%A2%E6%9C%A8%E7%B1%BB'.format(x)
到目前为止,您只需要更改范围即可抓取任意数量的页面。你快乐吗?你惊喜吗?
三只完美的爬行动物
如果只是按照上面的代码爬虫,爬了十几页之后程序很可能会崩溃。中途遇到过多次报错,导致爬虫失败。我终于写的爬虫,怎么说就崩溃了。
错误报告的原因有很多。玩爬虫的都知道调试bug很麻烦,需要不断的试错。这个爬虫的主要bug是TimeoutError。因此,我们需要进一步改进代码。
首先将上面的代码封装成函数,因为不使用函数有以下缺点:
1、复杂度增加
2、组织架构不够清晰
3、可读性差
4、代码冗余
5、可扩展性差
其次,在可能发生错误的地方添加异常处理。即尝试...除了。
完善后,截取部分,如下图。由于篇幅限制,我不会发布所有代码。需要完整代码的朋友,关注公众号,后台回复木头即可免费获取。
结语
此后,编写了红木数据爬虫代码,爬取数据后,可以直观的分析。比如可以看到每年不同市场红木的价格走势,同一市场不同红木的价格走势,也可以建立红木价格指数。后续我会重点介绍视觉内容,感兴趣的朋友可以关注一下~
当然,这个爬虫也有很大的改进空间,比如加入多线程,scrapy框架会爬得更快。另外,引入随机头和代理ip可以很好的避免一些反爬,很多比较复杂的爬虫都必须引入。