1、异步爬虫
高性能异步爬虫
2、多进程和多线程(不建议大家使用)
- 好处:可以为相关阻塞的操作单独开启线程或者进程,阻塞操作就可以异步执行
- 弊端:池中线程或进程的数量是有上限的。
- coroutinne:协程对象,我们可以将协程对象注册到事件循环中,它会被事件循环调用。
- 我们可以使用async 关键字来定义一个方法,这个方法在调用时不会立即被执行,而是返回一个协程对象。
- task:任务,他是对协程对象的进一步封装,包含了任务的各个状态
- future:代表将来执行或还没有执行的任务,实际上和task没有本质区别
- async:定义一个协程
- await:用来挂起阻塞方法的执行
在异步协程中如果出现了同步模块相关的代码,那么就无法实现异步
requests模块就是同步模块,所以就要换成aiohttp 模块来发请求 【不然实现不了异步】**
5、aiohttp 异步请求模块
pip install aiohttp
下载模块
# 定义一个函数
async def get_page(url):
async with aiohttp.ClientSession() as session:
async with await session.get/post(url) as response:
# 注意在获取响应数据操作之前 一定要使用 await 手动挂起
page_text = await reponse.text()
# text()方法返回字符串响应数据 和requests模块不同
# read()方法 返回二进制形式的响应数据
# json() 方法 返回json对象
6、多任务协程
import asyncio
import time
async def request(url):
print("正在下载", url)
# 在异步协程中如果出现了同步模块相关的代码,那么就无法实现异步
await asyncio.sleep(2)
print("下载完毕", url)
start = time.time()
urls = {
"www.baidu.com",
"www.vip.com",
"www.jd.com"
}
# 任务列表:存放多个任务对象
stasks = []
for url in urls:
c = request(url)
task = asyncio.ensure_future(c)
stasks.append(task)
loop = asyncio.get_event_loop()
# 需要将任务列表封装到wait中
loop.run_until_complete(asyncio.wait(stasks))
print(time.time() - start)
-----------------------------------------------------------------------------
import asyncio
async def request(url):
print("正在请求的url是:", url)
print("请求成功", url)
# async 修饰的函数,在调用后返回一个协程对象,不会立即执行
c = request("www.baidu.com")
# # 创建一个事件循环对象
# loop = asyncio.get_event_loop()
#
# # 将协程对象注册到loop中,然后启动loop
# loop.run_until_complete(c)
# -----------------------------------------------------------
# # task的使用 对协程的进一步封装
# # 将协程对象封装到任务对象
# loop = asyncio.get_event_loop()
# # 基于loop创建了一个task对象
# task = loop.create_task(c)
# # 注册task
# loop.run_until_complete(task)
# -----------------------------------------------------------
# -----------------------------------------------------------
# future的使用
loop = asyncio.get_event_loop()
future = asyncio.ensure_future(c)
# 注册future 执行future
loop.run_until_complete(future)
# -----------------------------------------------------------