Python爬虫7-多进程爬虫

       

目录

7.1多线程与多进程

7.1.1多线程和多进程概述

7.1.2多进程的使用方法

7.2综合案例-爬取简书网热评文章 

7.2.1爬虫思路分析

7.2.2爬虫代码及分析


        当数据的爬虫量越来越大的时候,除了要考虑存储的方式外,还需要考虑爬虫的速度问题。前面的爬虫都是串行爬取,只有当一次爬取完之后才进行下一次爬取,这样极大的限制了爬取的速度和效率。本章主要讲解多线程和多进程的概念,并通过案例对串行爬虫和多进程爬虫的性能进行对比,最后通过综合案例,讲解多进程爬取得方法和技巧。

7.1多线程与多进程

7.1.1多线程和多进程概述

        当计算机运行程序时,就会创建包含代码和状态得进程。这些进程会通过计算机的一个和多个CPU执行。不过,同一时刻每个CPU只会执行一个进程,然后再不同进程间快速切换,这样就给人以多个程序同时运行的感觉。同理,在一个进程中,程序的执行也是在不同线程间进行切换的,每个线程执行程序的不同部分。

        这里简单的做个类比:有一个大型工厂,该工厂负责生产玩具:同时工厂下又有多个车间,每个车间负责不同的功能,生产不同玩具的零件:每个车间里又有多个车间工人,这些工人互相合作,彼此共享资源来共同生产某个玩具零件等。这里的工厂就相当于一个网络爬虫,而每个车间相当于一个进程,每个车间工人相当于线程。这样,通过多线程和多进程,网络爬虫就能高效、快速的进行下去。

7.1.2多进程的使用方法

        Python进行多进程爬虫使用了multiprocessing库,此处使用multiprocessing库的进程池方法进行多进程爬虫,使用方法的代码如下。

from multiprocessing import Pool

pool = Pool(processes=4)        #创建进程池

pool.map(func,iterable[,chunksize])  #map函数运行进程,func参数为需要运行的函数,在爬虫实战中为爬虫函数。iterable为迭代参数,为url列表进行迭代

7.2综合案例-爬取简书网热评文章 

7.2.1爬虫思路分析

        (1)此次爬取的为简书网“首页投稿”热评文章的信息(首页投稿(暂停使用,暂停投稿) - 专题 - 简书

        (2)当手动浏览该网页时,会发现没有分页的界面,可以一直浏览下去,这说明该网页使用了异步加载技术。

        打开Chrome浏览器开发者工具(F12),选择Network选项卡,如下图

         通过鼠标手动下滑浏览网页,发现选项卡中加载了一些网址,后面明显标有page,所以就可以通过这个来构造URL

        (3)需要爬取的信息有:标题文章、文章内容、钻石数、用户ID、评论数、点赞数、打赏数

 

 7.2.2爬虫代码及分析

import requests
import pymongo
from lxml import etree
from multiprocessing import Pool

headers = {
    'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.93 Safari/537.36'
}

client = pymongo.MongoClient('localhost',27017)
mydb = client['mydb']
jianshu_shouye = mydb['jianshu_shouye']   #创建数据库和集合

def get_info(url):
    html = requests.get(url, headers=headers)
    selector = etree.HTML(html.text)
    infos = selector.xpath('//ul[@class="note-list"]/li')  # 取大标签循环
    for info in infos:
        title = info.xpath('div/a/text()')[0]
        content = info.xpath('div/p/text()')[0]
        zuanshis = info.xpath('div/div/span[1]/text()')
        if len(zuanshis) == 0:
            zuanshi = 0
        else:
            zuanshi = zuanshis[1].strip()
        author = info.xpath('div/div/a[1]/text()')[0]
        comments = info.xpath('div/div/a[2]/text()')
        if len(comments) == 0:
            comment = 0
        else:
            comment = comments[1].strip()
        likes = info.xpath('div/div/span[2]/text()')
        if len(likes) == 0:
            like = 0
        else:
            like = likes[0].strip()
        rewards = info.xpath('div/div/span[3]/text()')
        if len(rewards) == 0:
            reward = "无"
        else:
            reward = rewards[0].strip()
        data = {
            'title':title,
            'content':content,
            'zuanshi':zuanshi,
            'author':author,
            'comment':comment,
            'like':like,
            'reward':reward
        }
        print(data)
        jianshu_shouye.insert_one(data)

if __name__=='__main__':
    urls = ['https://www.jianshu.com/c/bDHhpK?order_by=top&page={}'.format(str(i)) for i in range(1,10)]
    pool = Pool(processes=2)
    pool.map(get_info,urls)

        代码与平常的代码没什么好说的,就是针对数据而言,我们要对爬取的东西作为判断,在简书这个网页,举个栗子,有的文章有钻石数而有的却没有,这时就需要做出来明确判断的代码,否则在某个环节会出现INdexError,如果在整个代码块上使用try···except可能就会跳过很多文章。对于不同的网页构造出合理的代码,那才是我们学习的初衷。

  • 3
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值