本文介绍: 爬虫时遇到很多数据并不在访问网址返回包里,而是随着用户下拉逐步加载的,也就是用到了Ajax,那么这时我们如何爬取我们想要的数据呢?

爬虫时遇到很多数据并不在访问网址返回包里,而是随着用户下拉逐步加载的,也就是用到了Ajax,那么这时我们如何爬取我们想要的数据呢?这里爬取b评论区相关数据为例,练习一下python爬虫异步爬取数据的相关流程,完整程序实例最后面:

准备工作

用到的包:

import requests

import time

爬虫相关主要还是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)#试试看抓不抓得到

 可以看到抓到了对应的数据,接下来就对抓到的数据进行处理,找到我们想要的相关信息

数据处理

准备一个空的list存放想要的数据:

result = []

然后在那一堆JSON数据中找到我们想要的数据对应的键值,例如我需要评论区用户的昵称。按照如下顺序找到对应标签

于是通过以下语句可以将抓到的信息保存result中:

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格式

爬到之后自然要存起来,这里爬取bid+等级两个元素为例介绍怎么把得到的结果存到.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")

这样操作之后就会在当前根目录文件夹生成一个.csv文件: 

里面着数据:

 示例代码

代码示例如下

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进行投诉反馈,一经查实,立即删除

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注