百度网页关键字抓取(学习Python,就避免不了爬虫,而Scrapy就是最简单的图片爬虫)

优采云 发布时间: 2021-09-10 23:12

  百度网页关键字抓取(学习Python,就避免不了爬虫,而Scrapy就是最简单的图片爬虫)

  学习Python离不开爬虫,Scrapy是最受欢迎的。可以爬取文字信息(比如职位信息、网站评论等),也可以爬取图片,比如看到一些不错的网站展示了很多漂亮的图片(这里仅供个人学习Scrapy使用,不是用于商业用途),您可以下载它。好了,话不多说,下面开始一个简单的图片爬虫。

  首先,我们需要一个浏览器来方便的查看html路径。建议使用火狐开发版() 这个版本的火狐标志是蓝色的

  安装这个之后就不需要安装firebug、firepath等插件了

  这里的例子,以花瓣网为例,抓取本页图片。

  第一步:打开火狐浏览器,使用上面的网址访问,导航到Inspector选项卡,点击箭头然后选择一张图片,你就可以看到所选图片的位置(见下图)

  

  这里我们发现打开的页面收录很多主题的图片,每个主题对应一个图片链接地址。打开后就是这个话题对应的图片。那么我们的目的就是抓取每个话题下的图片,所以第一步就是获取每个话题的链接,打开链接,查看图片地址,一一下载。现在我大概知道我们的例子有两层结构:①访问首页,展示不同主题的图片 ②打开每个主题,展示主题下方的图片

  现在开始创建scrapy项目(可以参考前面的文章)

  这里我创建了一个huaban2项目(我之前又做了一个,所以这里就命名为huaban2,随便我想),然后我创建了一个spider,begin是一个命令行文件,里面是scrapy Crawl meipic的命令,见稍后

  

  第 2 步:实现蜘蛛

  # -*- coding: utf-8 -*-

from huaban2.items import Huaban2Item

import scrapy

class HuabanSpider(scrapy.Spider):

name = 'meipic'

allowed_domains = ['meisupic.com']

baseURL = 'http://www.meisupic.com/topic.php'

start_urls = [baseURL]

def parse(self, response):

node_list = response.xpath("//div[@class='body glide']/ul")

if len(node_list) == 0:

return

for node in node_list:

sub_node_list = node.xpath("./li/dl/a/@href").extract()

if len(sub_node_list) == 0:

return

for url in sub_node_list:

new_url = self.baseURL[:-9] + url

yield scrapy.Request(new_url, callback=self.parse2)

def parse2(self, response):

node_list = response.xpath("//div[@id='searchCon2']/ul")

if len(node_list) == 0:

return

item = Huaban2Item()

item["image_url"] = node_list.xpath("./li/a/img/@data-original").extract()

yield item

  解释一下这段代码:使用scrapy genspider meipic生成蜘蛛后,已经写好了默认结构,这里我们设置了一个baseURL,默认方法是parse。从上面的分析我们知道需要获取每个topic的链接,所以我们使用xpath来定位

  node_list = response.xpath("//div[@class='body glide']/ul")

  这样我们就得到了一个selector对象,赋值给变量node_list,加一个if判断,如果没了就结束(return后的代码不会被执行,这个大家应该都知道),然后我们要取/ul/下li/dl下的href,用extract()返回一个list,就是dl下的所有链接。接下来,我们需要拼接一个完整的 URL,然后请求这个 URL,并用 yield 返回。因为我们真正要抓取的图片在页面的第二层,所以这里的回调函数调用了一个parse2(这是我自己定义的一个方法),parse2是用来处理图片链接的。同理,从之前拼接的URL请求页面返回parse2的响应

  

  这里我们要获取图片的地址,就是//div[@id='SearchCon2']/ul/li/a/img/@data-original,获取到地址后,交给item (我们定义了item字段用来存放图片的地址),这样item返回到管道中

  items.py

  import scrapy

class Huaban2Item(scrapy.Item):

# define the fields for your item here like:

# name = scrapy.Field()

image_url = scrapy.Field()

image_paths = scrapy.Field()

  管道.py

  from scrapy.pipelines.images import ImagesPipeline

from scrapy.exceptions import DropItem

import scrapy

class Huaban2Pipeline(ImagesPipeline):

def get_media_requests(self, item, info):

for image_url in item['image_url']:

yield scrapy.Request(image_url)

def item_completed(self, results, item, info):

image_paths = [x["path"] for ok, x in results if ok]

if not image_paths:

raise DropItem("Item contains no image")

item['image_paths'] = image_paths

return item

  因为要下载图片,所以需要在settings.py中配置一个路径,同时

  需要的配置如下,其他默认即可

  MEDIA_ALLOW_REDIRECTS = True #因为图片地址会被重定向,所以这个属性要为True

IMAGES_STORE = "E:\\img" #存储图片的路径

ROBOTSTXT_OBEY = False #Robot协议属性要为False,不然就不会抓取任何内容

ITEM_PIPELINES = {

'huaban2.pipelines.Huaban2Pipeline': 1,

} #pipeline要enable,不然不会出来pipeline的请求

  最后我们写了一个begin.py文件来执行

  from scrapy import cmdline

cmdline.execute('scrapy crawl meipic'.split())

  多说一点,可以存储不同大小的图片,如果需要,可以在settings.py中添加属性

  IMAGES_THUMBS = {'small': (100, 100), 'big': (800, 1000)}

  好了,基础写完了,可以开始执行了。

0 个评论

要回复文章请先登录注册


官方客服QQ群

微信人工客服

QQ人工客服


线