前言

因为需要一些图片素材,又不想一个个手动下载,遂通过爬虫来解放双手。在百度图片中搜索“汉服美女”,然后以浏览器地址栏上的地址作为初始 URL。通过对 URL 分析知道 URL 分为 3 部分:域名 + 固定参数 + 关键字参数。

爬取

#!/usr/bin/env python
# -*- coding: utf-8 -*-# @author: Nancy
# @contact: fweiren@163.com
# @software: PyCharm
# @file: getHanfu.py
# @time: 2019/2/23 14:34import requests
import re
import timeclass BaiduPictures(object):def __init__(self, keyboard):self.headers = {"user-agent": "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/66.0.3355.4 Safari/537.36"}self.base_url = "https://image.baidu.com"self.keyboard = str(keyboard)def send_request(self, url):""":param url: 网址:return: unicode 型数据"""try:html = requests.get(url, headers=self.headers).textreturn htmlexcept Exception as e:print(e)def make_request(self, url):""":param url: 网址:return: bytes 型数据 (二进制的数据)"""try:html = requests.get(url, headers=self.headers).contentreturn htmlexcept Exception as e:print(e)def load_page(self, html):pattern = r'"objURL":"(http.*?)",'img_urls = re.findall(pattern, html)for img_url in img_urls:img_puffix = img_url.rsplit(".", 1)[1].lower()t = time.time()now_time = str(round(t * 1000))data = self.make_request(img_url)if data and img_puffix in ['jpg', 'jpeg', 'png']:self.write_pic(data, now_time + "." + img_puffix)elif data:self.write_pic(data, now_time + ".jpg")else:print(img_url + u"地址无效")# data = self.make_request(img_url + ".jpg")# if data:#     self.write_pic(data, now_time + ".jpg")def write_pic(self, data, filename):print(u"[INFO]: 正在下载:%s..." % filename)with open(u"E:\images\img" + filename, 'wb') as f:f.write(data)def start(self):html = self.send_request(self.base_url + "/search/index?tn=baiduimage&ipn=r&ct=201326592&cl=2&lm=-1&st=-1" +"&sf=1&fmq=&pv=&ic=0&nc=1&z=&se=1&showtab=0&fb=0&width=&height=&face=0" +"&istype=2&ie=utf-8&fm=index&pos=history&word=" + self.keyboard)self.load_page(html)if __name__ == "__main__":keyboard = input("请输入关键词:")Pictures = BaiduPictures(keyboard="汉服美女")Pictures.start()

注意:上述代码中会出现图片地址中无后缀,如下图所示。

进阶

通过上方代码,我们会发现只能下载 30 张图片,这是因为百度图片是动态加载的,它的网页原始数据其实是没有这个图片的,通过运行 JavaScript,把这个图片数据插入到网页的 html 标签中,那这样造成的结果是,我们在开发者工具中虽然能看到这个 html 标签,但实际上,当我们在看网页的原始数据的时候,其实是没有这个标签的,它只在运行时加载和渲染,那这个时候怎么办呢?怎么把这个图片给下载下来呢?这里面我们就换一个思路:抓包。

按F12打开开发者工具,点击 Network–XHR,然后向下滑动滚动条,会一直出现一个名为:acjson?tn=resultjson_com…的请求,点击它再点击 Preview,会发现这是 json 数据,点开 data,会看到里面有 30 条数据,每一条都对应着一张图片。

这下明白了吧,百度图片一开始只加载 30 张图片,当我们往下滑动滚动条时,页面会动态加载 1 条 json 数据,每条 json 数据包含 30 条信息,信息里又包含图片的 URL,JavaScript 会将这些 URL 解析并显示出来。这样,每次滚动到底就又多出 30 张图片。

那么,这些一直出现的 json 数据有什么规律呢?我们点击 Headers,然后对比这些 json 数据的头部信息。通过对比,我们发现 Headers 下的 Query String Parameters 中的字段大多保持不变,只有 pn、gsm 字段不同,而 pn 每次递增 30,以及最后的时间戳不断变化。

代码

#!/usr/bin/env python
# -*- coding: utf-8 -*-# @author: Nancy
# @contact: fweiren@163.com
# @software: PyCharm
# @file: getHanfu.py
# @time: 2019/2/23 14:34import requests
import re
import timeclass BaiduPictures(object):def __init__(self, keyboard):self.headers = {"user-agent": "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/66.0.3355.4 Safari/537.36"}self.base_url = "https://image.baidu.com"self.keyboard = str(keyboard)def send_request(self, url):""":param url: 网址:return: unicode 型数据"""try:html = requests.get(url, headers=self.headers).textreturn htmlexcept Exception as e:print(e)def make_request(self, url):""":param url: 网址:return: bytes 型数据 (二进制的数据)"""try:html = requests.get(url, headers=self.headers).contentreturn htmlexcept Exception as e:print(e)def load_page(self, html):pattern = r'"objURL":"(ippr.*?)",'encrypted_urls = re.findall(pattern, html)for encrypted_url in encrypted_urls:t = time.time()now_time = str(round(t * 1000))                  # 时间戳img_url = self.url_complie(encrypted_url)        # 解密 objURL 地址img_puffix = img_url.rsplit(".", 1)[1].lower()   # 图片格式后缀data = self.make_request(img_url)if data and img_puffix in ['jpg', 'jpeg', 'png']:self.write_pic(data, now_time + "." + img_puffix)elif data:self.write_pic(data, now_time + ".jpg")else:print(img_url + u"地址无效")# data = self.make_request(img_url + ".jpg")# if data:#     self.write_pic(data, now_time + ".jpg")def url_complie(self, url):""":param url: 加密的 objURL 地址ex: ippr_z2C$qAzdH3FAzdH3Ft42_z&e3Bh7p55b_z&e3Bv54AzdH3F7rs5w1AzdH3Ft4w2jAzdH3Fm90nlb0mAzdH3Fdc_lmaxc9a_z&e3B3r2:return: 解密 URL"""res = ''c = ['_z2C$q', '_z&e3B', 'AzdH3F']d = {'w': 'a', 'k': 'b', 'v': 'c', '1': 'd', 'j': 'e', 'u': 'f', '2': 'g', 'i': 'h', 't': 'i', '3': 'j','h': 'k', 's': 'l', '4': 'm', 'g': 'n', '5': 'o', 'r': 'p', 'q': 'q', '6': 'r', 'f': 's', 'p': 't','7': 'u', 'e': 'v', 'o': 'w', '8': '1', 'd': '2', 'n': '3', '9': '4', 'c': '5', 'm': '6', '0': '7','b': '8', 'l': '9', 'a': '0', '_z2C$q': ':', '_z&e3B': '.', 'AzdH3F': '/'}if url is None or 'http' in url:return urlelse:j = urlfor m in c:j = j.replace(m, d[m])for char in j:if re.match('^[a-w\d]+$', char):char = d[char]res = res + charreturn resdef write_pic(self, data, filename):print(u"[INFO]: 正在下载:%s..." % filename)with open(u"E:\images\img" + filename, 'wb') as f:f.write(data)def start(self):for page in (30, 121, 30):html = self.send_request(self.base_url + "/search/acjson?tn=resultjson_com&ipn=rj&ct=201326592&is=&fp=result&queryWord=" + self.keyboard +"&cl=2&lm=-1&ie=utf-8&oe=utf-8&adpicid=&st=-1&z=&ic=0&hd=&latest=&copyright=&word=" + self.keyboard +"&s=&se=&tab=&width=&height=&face=0&istype=2&qc=&nc=1&fr=&expermode=&force=&pn=" + str(page) +"&rn=30&gsm=1e&1551881855622=")print(self.load_page(html))if __name__ == "__main__":keyboard = input("请输入关键词:")Pictures = BaiduPictures(keyboard="汉服美女")Pictures.start()

参考

python requests的content和text方法的区别

python百度图片爬取
python学习(7):python爬虫之爬取动态加载的图片,以百度图片为例
百度返回的JSON数据解析返回的objURL(python版本)

[Python3] 爬取百度图片到本地相关推荐

  1. python3爬取百度图片

    python3爬取百度图片 最终目的:能通过输入关键字进行搜索,爬取相应的图片存储到本地或者数据库 首先打开百度图片的网站,搜索任意一个关键字,比如说:水果,得到如下的界面 分析: 1.百度图片搜索结 ...

  2. python3 爬取百度图片

    深度学习中,从网上下载大量的图片数据,肯定是必须的.作为python爬虫小白,记录一下此过程. 一.分析网页结构 1.在百度图片中输入狗,得到如下所示的网址 http://image.baidu.co ...

  3. json返回的img图片被原样输出_爬取百度图片,并下载至本地

    爬取百度图片 一:本节目标 本次爬取的目标是百度图片,将图片下载到本地 二:准备工作 安装Scrapy.Python3 三:爬取思路 我们需要实现的是下载图片,所以需要获取图片的真实链接 四:爬取分析 ...

  4. 用python3爬取百度首页

    用python3读取百度首页 代码 爬取百度首页 import urllib.request import urlliburl="http://www.baidu.com/" ht ...

  5. Java爬取百度图片人脸识别下载高颜值小姐姐图片

    前言: 最近想下载一些比较好看的妹子图片,但又不想去网上一张张的看,于是就想通过爬取图片进行人脸识别下载. 1.首先:在爬取图片时,通过Java请求时会遇到百度安全认证机制,在这里可以模拟浏览器的请求 ...

  6. Python 爬虫实例(1)—— 爬取百度图片

    爬取百度图片  在Python 2.7上运行 #!/usr/bin/env python # -*- coding: utf-8 -*- # @Author: loveNightimport json ...

  7. python爬取百度图片(用于深度学习中数据集的收集)

    6_python爬取百度图片(用于深度学习中数据集的收集)(6-20181225-) 参考: https://blog.csdn.net/guyuealian/article/details/7873 ...

  8. 如何使用python爬取百度图片_python实现爬取百度图片的方法示例

    本文实例讲述了python实现爬取百度图片的方法.分享给大家供大家参考,具体如下: import json import itertools import urllib import requests ...

  9. python爬去百度图片_python实现爬取百度图片的方法示例

    本文实例讲述了python实现爬取百度图片的方法.分享给大家供大家参考,具体如下: import json import itertools import urllib import requests ...

最新文章

  1. go get 无法下载问题解决方案及下载 aliyun-oss-go-sdk incompatible.info
  2. php mod11 10公式,AQL RQL
  3. BEX5下新建任务到待办任务
  4. I.MX6 GPS JNI HAL register init hacking
  5. onclick实现超链接_给超链接加onclick事件
  6. 产品经理必须知道的一点知识:三种方法判断一个产品该不该做
  7. android 录音命令,音频延迟  |  Android NDK  |  Android Developers
  8. UVA - 10534
  9. js中eval的用法
  10. 计算机网络及分布式系统
  11. java实现微博热搜榜_微博热搜数据
  12. 高阶整车域控制器的详细设计方案
  13. JS:鼠标事件:实现鼠标移动到div背景颜色变换,移开还原
  14. 安装win7时,显示缺少所需的CD/DVD驱动器设备驱动程序
  15. 【OpenGrok代码搜索引擎】一、OpenGrok简介
  16. Java压缩背景透明图片后图片背景变成黑底
  17. image失败 安装scikit_安装SciKitImage错误127
  18. 一键检测Linux VPS/服务器配置、IO、国内节点下载测速
  19. 网上免费平台学习美术
  20. 石英晶振常用术语解释

热门文章

  1. mysql和虚拟主机区别_什么是mysql虚拟主机?mysql虚拟主机有哪些优势?
  2. 某内Java课程(整套视频+课件)
  3. vue使用expres
  4. 捧起同声传译圣杯的AI:向人类偷师、与人类共事
  5. win10 实现多用户同时远程访问
  6. 程序员无休止加班的真正原因是
  7. 富文本编辑器Tinymce超简单使用
  8. 怎么选择计算机等级考试科目?里面有学问...
  9. 【论文翻译】Machine learning: Trends,perspectives, and prospects
  10. 链接fiddler以后,提示网络不可用的解决方法