爬虫时遇到很多数据并不在访问网址的返回包里,而是随着用户下拉逐步加载的,也就是用到了Ajax,那么这时我们该如何爬取我们想要的数据呢?这里用爬取b站评论区相关数据为例,练习一下python爬虫异步爬取数据的相关流程,完整程序实例在最后面:
准备工作
用到的包:
爬虫相关主要还是requests包,练习用脚本本身也并不复杂。
根据写一个爬虫脚本的一般流程,第一步显然是找到含有我们需要信息的相关网页链接,这里我们的目标是b站的评论区。随便点开一个视频。
评论区下拉的过程中会发现下面列表多出来很多条目,这些就是网页向服务器请求的资源。找一找评论相关的那条,如下,对应的响应内容就是我们需要的信息,其中对应的这个链接也是我们待会写爬虫时要用到的链接:
这个响应是JSON格式的,JSON是一种数据格式。我们可以把它alt+a全选之后放到JSON解析器里,这样就能清晰的看到它的结构,类似的解析器百度就可以搜到:
可以看到信息主要都是由一个个键值对组成,前面双引号里的是它的标签,后面是这个条目具体的值,也就是评论内容,用户名等等信息都在这里。可以看到评论内容等信息,说明这就是我们要找的:
爬虫连接资源
第一步当然是连接目标地址,这里的url用的就是上面网络里请求资源的那个链接,记得加上请求头:
url = f'https://api.bilibili.com/x/v2/reply/main?csrf=ee494c6f80d497b7453d4acfa7f0e3de&mode=2&next=0&oid=680890718&plat=1&seek_rpid=&type=1'#资源对应链接
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:98.0) Gecko/20100101 Firefox/98.0',
}#请求头
response = requests.get(url=url, headers=headers)#连接
response.encoding = 'utf-8'#设置编码方式
printf(response.json)#试试看抓不抓得到
可以看到抓到了对应的数据,接下来就对抓到的数据进行处理,找到我们想要的相关信息:
数据处理
result = []
然后在那一堆JSON数据中找到我们想要的数据对应的键值,例如我需要评论区用户的昵称。按照如下顺序找到对应标签:
for j in response.json()['data']['replies']:
result.append(j['member']['uname'])
print(result)
类似的比如评论内容就是data->replies->content->message
for j in response.json()['data']['replies']:
result.append(j['content']['message'])
print(result)
还可以把多个元素接到一起,就像这样,接在一起的元素可以通过split分割成多维数组,方便后面保存。:
for j in response.json()['data']['replies']:
result.append(j['member']['uname']+','+str(j['member']['level_info']['current_level']))
result = [i.split(',') for i in result]
爬取异步数据
通过上面方式得到的数据实际上只是一次请求的数据,在我们往下拉的时候不断有新评论传过来,下面来实现异步抓取评论信息。
观察链接:
发现在异步请求数据的过程中next的值改变了,也就是说我们只要改变链接中next的值哦,就可以爬取到后续的信息,于是改变url如下,注意多次请求时中间停一会,不要对网站造成影响,最后爬下来数据可能会有重复,可以用set方法去重后再做后续处理::
for i in range(0,10):
time.sleep(1)
url = f'https://api.bilibili.com/x/v2/reply/main?csrf=ee494c6f80d497b7453d4acfa7f0e3de&mode=2&next={i}&oid=680890718&plat=1&seek_rpid=&type=1'
......
result = list(set(result))
保存数据(.csv格式)
爬到之后自然要存起来,这里以爬取b站 id+等级两个元素为例介绍怎么把得到的结果存到.csv文件里,首先需要把爬到的用逗号分隔的两个元素组成的裂变变成二维列表,然后用withopen写入.csv文件中。
for j in response.json()['data']['replies']:
result.append(j['member']['uname']+','+str(j['member']['level_info']['current_level']))
result = list(set(result))
result = [i.split(',') for i in result]
with open('bili.csv', 'w', newline='') as csvfile:
writer = csv.writer(csvfile)
# 写入数据
writer.writerows(result)
print("Writing complete")
示例代码
import requests
import time
import csv
result = []
for i in range(0,10):
time.sleep(1)
url = f'https://api.bilibili.com/x/v2/reply/main?csrf=ee494c6f80d497b7453d4acfa7f0e3de&mode=2&next={i}&oid=680890718&plat=1&seek_rpid=&type=1'
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:98.0) Gecko/20100101 Firefox/98.0',
}
response = requests.get(url=url, headers=headers)
response.encoding = 'utf-8'
# print(response.json())
for j in response.json()['data']['replies']:
result.append(j['member']['uname']+','+str(j['member']['level_info']['current_level']))
result = list(set(result))
result = [i.split(',') for i in result]
# print(result)
with open('bili.csv', 'w', newline='') as csvfile:
writer = csv.writer(csvfile)
# 写入数据
writer.writerows(result)
print("Writing complete")
注意进行爬虫相关操作时遵守法律法规,不要爬取隐私信息,代码仅供参考。
原文地址:https://blog.csdn.net/qq_46145027/article/details/130010385
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.7code.cn/show_15579.html
如若内容造成侵权/违法违规/事实不符,请联系代码007邮箱:suwngjj01@126.com进行投诉反馈,一经查实,立即删除!