编译器:Pycharm community 2018.3.4版本
数据库:Mysql 5.5 / SQLyog
首先我们介绍一下为什么用多进程爬虫,目的是为了提升爬虫的爬取速度,更快的获取速度,众所周知Python的缺点是速度慢,用多进程可以很好的弥补。
1.引用头部的包
from multiprocessing import Pool
2.构造一个函数(下面再详细的写)
def get_comment(url):
web_data = requests.get(url, headers=headers, proxies=proxies)
web_data.raise_for_status()#检测是否能访问
web_data.encoding = web_data.apparent_encoding#
soup = BeautifulSoup(web_data.text, "lxml")#用lxml解析
//获取网页信息,爬取内容等等//
......
3.用多进程运行
pool = Pool(processes=3)#这里的processes就代表三个进程
pool.map(get_comment, urls)#pool的map方法传入的参数分别是(函数,可迭代对象)
pool.close()
pool.join()#多个进程的携程,分配资源
接下来在写具体的代码前,先跟大家介绍一下:进程并不是越多越好,当进程过多的时候会互相争夺资源,从而降低了速度,作者这里实验得到三进程的爬取速度比较适宜,大家也可以试试进程数不同时的速度。
4.具体代码部分
头部引用:
import requests
import time #引用time库记录总耗时
import pymysql #引用链接mysql的数据库
from bs4 import BeautifulSoup #引用Beautifulsoup库
from multiprocessing import Pool #引用pool方法
import random #引用random库随机抽取IP池里的地址
headers ={'User_Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) '
'AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3497.100 Safari/537.36'}
#请求头的伪装,伪装成浏览器,可以用谷歌开发者工具查看
proxy_list = [
'http://140.224.76.21:808',
'http://60.178.14.90:8081',
'http://121.232.146.13:9000',
]
# IP池的制作
proxy_ip = random.choice(proxy_list) # 随机获取IP地址
proxies = {'http': proxy_ip}
#链接Mysql数据库 host=localhost user=用户名 db=数据库名 port=3306
conn = pymysql.connect(host = 'localhost',user = 'root',passwd = '123456',
db = 'bigdata',port = 3306,charset = 'utf8')
#用ursor提供的方法来进行工作.这些方法包括两大类:1.执行命令,2.接收返回值
item = conn.cursor()
函数部分:
def get_comment(url):
#获取数据,调用请求头,代理池。
web_data = requests.get(url, headers=headers, proxies=proxies)
web_data.raise_for_status() #检查是否成功返回数据
web_data.encoding = web_data.apparent_encoding #更改编码
soup = BeautifulSoup(web_data.text, "lxml")
'''处理爬取数据'''
#用find-all方法解析文本 获取数据
titles = soup.find_all('a',attrs={"class":"pc_temp_songname"})
ranks = soup.find_all('span',attrs={"class":"pc_temp_num"})
times = soup.find_all('span',attrs={"class":"pc_temp_time"})
for title, rank, time in zip(titles, ranks, times):
#把所有获取的 titles, ranks, times 打包成一个zip()对象,并遍历。
title = title.get_text().split('-')[-1].strip()
rank = rank.get_text().strip()
time = time.get_text().strip()
#对数据的插入操作
item.execute('insert into value(title,rank,time) values(%s,%s,%s)', (str(title),str(rank),str(time)))
conn.commit()
#数据库链接,这里有个坑要注意
#(多进程一定要把链接语句封装到函数里,不然无法返回数据)
运行部分:
if __name__ == '__main__':
#构造URL列表
urls = ['https://www.kugou.com/yy/rank/home/{}-8888.html?from=rank'.format(str(number))
for number in range(1,24)]
start_time = time.time()#开始计时
pool = Pool(processes=3)#开启三个进程
pool.map(get_comment, urls)
pool.close()
pool.join()
end_time = time.time()#结束计时
#计算总时间
print('四进程爬虫的时间是:', end_time - start_time)
5.运行结果