IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> Python知识库 -> 基于python 爬取bing百度引擎检索的图片程序设计,附有基于该源码开发的软件不用配环境 -> 正文阅读

[Python知识库]基于python 爬取bing百度引擎检索的图片程序设计,附有基于该源码开发的软件不用配环境

python 爬取bing,百度检索到图片

一、前言

??我在进行视觉AI的训练时候,发现没有啥数据集是完美包含我要的类别,思来索去还是直接爬取互联网上的来的香。
??检索图片的质量上就谷歌,bing,百度比较多也比较好,sogou和360做了些反爬,我突破不了就算了,谷歌需要翻墙比较麻烦。最终图片数据来源目标就定在bing和百度了。
??谷歌爬取图片有需要的可以尝试一波

二、爬取百度引擎检索的图片程序设计

1、百度网页源码分析:检索网页源码中的哪个属性包含图片url

F12----》选择网络----》选择XHR----》F5刷新页面
点击抓包的请求----》预览
在这里插入图片描述
在这里插入图片描述

获取信息分析如下:

  • 通过对属性middleURL的模式匹配得到图片的地址
  • 每次请求,可以获取30个图片的下载地址

2、百度网页源码分析:根据上一步获取的属性middleURL寻找re模式

下载当前页面的网页源码
在这里插入图片描述

保存到txt文档中----》ctrl+F检索属性middleURL
在这里插入图片描述
获取信息分析如下:

  • url就在属性middleURL的后面,且都有固定的格式
  • 获取匹配图片url模式:r’“middleURL”:“(.*?)”’

3、百度网页源码分析:对比不同请求的链接差异

目的:以此达到自动“翻页”下载的效果

点击不同的请求,复制三个链接地址
在这里插入图片描述
粘贴到一个txt文档中进行对比
在这里插入图片描述
这样我们就知道怎么“伪造请求”了

4、爬取百度图片的程序设计

程序设计思路

  1. 创建文件夹,并将当前目录转化到该文件夹
  2. 根据模式r’“middleURL”:“(.*?)”',设计一个函数geturls,获取当前请求内的全部图片urls
  3. 设计函数DownloadImg(),输入urls,对每一个urls,进行访问并下载
  4. 如果下载图片个数达到定义的数量就自动终止
#coding=utf-8
import re
import time
import requests
from urllib import parse #对汉字进行编码
import os
#用来随机抽头发出申请
import random
from fake_useragent import UserAgent #随机生成一个user-agent,模拟有多个浏览器访问
import urllib3


'''
函数功能
返回一个url页面里面全部图片超链接的列表
'''
dic={'bing':r'img.*src="(.*?)"','baidu':r'"middleURL":"(.*?)"','sogou':r'img.*src="(.*?)"','360':r'"img":"(.*?)"'}
def writeHtml(url,html):
    with open(url,'w',encoding='utf-8') as f:
        f.write(str(html))

def geturls(baseurl,enginPattern):
    Img = re.compile(enginPattern)  # 正则表达式匹配图片,匹配bing搜索
    # 头,假装我是浏览器访问的网页
    headers ={'User-Agent':UserAgent().random}
    urllib3.disable_warnings()
    response = requests.get(baseurl, headers=headers)  # 获取网页信息

    html = response.text        # 将网页信息转化为text形式
    data=re.findall(Img, html)  # 存储图片超链接的列表
    return data                 # 返回一个包含该页面全部图片超链接的新列表

def DownloadImg(imgUrls):
    global i
    # 头,假装我是浏览器访问的网页
    headers={'User-Agent':UserAgent().random}
    for ImgUrl in imgUrls:
        if i < imgNum:
            try:  # 如果url是无效的,则查看下一个url
                resp = requests.get(ImgUrl, headers=headers)  # 获取网页信息
            except requests.ConnectionError as e:
                continue
            byte = resp.content  # 转化为content二进制

            with open("{:0>4d}.jpg".format(i + 1), "wb") as f:  # 文件写入
                if resp.status_code==200 and len(str(byte)) > 1000  :  # 访问成功且返回的值大于1000
                    f.write(byte)
                    # print(len(str(byte)))
                    i = i + 1        # 递增,表示又多下载了一张图片
                    time.sleep(0.5)  # 每隔0.5秒下载一张图片放入D://情绪图片测试
                    print("第{}张与{}有关的图片爬取成功!".format(i, search))
        else:
            break

search=input('请输入检索词:') #检索词
imgNum=int(input('请输入爬取图片数量:'))  #爬取图片数量
engine='baidu' #要爬取的引擎,有效值有:bing,baidu,360
i=0

def main():
    if not os.path.isdir("./{}_{}".format(search,engine)):#确定文件夹一定存在
        os.mkdir("./{}_{}".format(search,engine))
    os.chdir("./{}_{}".format(search,engine))             #确保当前目录位于search目录,图片将保存在这一目录
    global i  # 图片名递增,并用于判断图片数量是否达到imgNum

    while(i<imgNum):
        for index in range(10000):#预估一个最大页数,不可能超过这个页数的
            decteUrl='https://image.baidu.com/search/acjson?tn=resultjson_com&logid=7542812996841482750&ipn=rj&ct=201326592&is=&fp=result&fr=&word={}&queryWord={}&cl=2&lm=-1&ie=utf-8&oe=utf-8&adpicid=&st=-1&z=&ic=0&hd=&latest=&copyright=&s=&se=&tab=&width=&height=&face=0&istype=2&qc=&nc=1&expermode=&nojc=&isAsync=&pn={}&rn=30&gsm=1e&{}='.format(parse.quote(search),parse.quote(search),index*30,str(int(time.time()*1000)))

            imgUrls=geturls(decteUrl,dic[engine])
            DownloadImg(imgUrls)

            if i>=imgNum:
                break
    if(i==imgNum):
        print("已基于搜索引擎{}爬取了{}张与{}相关的图片,保存在文件夹{}\{}_{}".format(engine,imgNum,search,os.getcwd(),search,engine))
if __name__ == '__main__':
    main()

三、利用字典综合bing、百度两个引擎爬取图片的程序设计

1、检索bing对当前页面html中匹配到图片链接的模式

F12查看当前网络源码,利用当鼠标移动到那个块,哪个块就会高亮标记的特点
锁定,该图片所对应的块,
在这里插入图片描述

将其复制到txt文件中
在这里插入图片描述
获取信息分析如下:

  • 从html中获取图片的地址,模式为:‘’‘<img class=“mimg vi.src="(.?)”’
    注:这个模式,有时候是比较随心的,就是看着匹配

2、检索bing如何,调控链接来实现翻页

在源码中查询,不同请求链接的差别
在这里插入图片描述
将不同请求粘贴到txt文本中对比,差异。
在这里插入图片描述
获取信息分析如下:

  • 可以通过修改first实现翻页

3、源码

思路:

  • 在之前爬取百度图片的基础上,加入dicPattern字典,和dicUrl字典,分别保存从网页源码中搜索图片地址的模式,bing和百度的链接
#coding=utf-8
import re
import time
import requests
from urllib import parse #对汉字进行编码
import os
#用来随机抽头发出申请

from fake_useragent import UserAgent #随机生成一个user-agent,模拟有多个浏览器访问
import urllib3



class ImgGenerate:
    def __init__(self,engine,search,maxNum,outFile):
        self.dicPattern={'bing':r'<img class="mimg vi.*src="(.*?)"','baidu':r'"middleURL":"(.*?)"','sogou':r'img.*src="(.*?)"','360':r'"img":"(.*?)"'}
        self.dicUrl={'bing':'https://cn.bing.com/images/search?q={}&form=HDRSC2&first={}&tsc=ImageHoverTitle','baidu':'https://image.baidu.com/search/acjson?tn=resultjson_com&logid=7542812996841482750&ipn=rj&ct=201326592&is=&fp=result&fr=&word={}&queryWord={}&cl=2&lm=-1&ie=utf-8&oe=utf-8&adpicid=&st=-1&z=&ic=0&hd=&latest=&copyright=&s=&se=&tab=&width=&height=&face=0&istype=2&qc=&nc=1&expermode=&nojc=&isAsync=&pn={}&rn=30&gsm=1e&{}='}
        self.engine = engine  #检索引擎
        self.search =search   #检索词
        self.Dowdnum=0        #当前已经下载数量
        self.imgNum =maxNum   #下载数量
        self.outFile=outFile  #下载图片的地址

        try:
            # 确保当前目录位于search目录,图片将保存在这一目录
            os.chdir(self.outFile)

            if not os.path.isdir("./{}_{}".format(search,engine)):  # 确定文件夹一定存在
                os.mkdir("./{}_{}".format(search,engine))
            os.chdir("./{}_{}".format(search,engine))
        except:
            print("请输入正常的检索词")
    '''
    函数功能
        输入一个地址和,网页源码,
        将源码写入txt文本,便于浏览
    '''
    def writeHtml(self,outfile,html):
        with open(outfile,'w',encoding='utf-8') as f:
            f.write(str(html))

    '''
    函数功能
        返回一个url页面里面全部图片超链接的列表
    '''
    def geturls(self,baseurl,enginPattern):
        ImgUrlPattern = re.compile(enginPattern)  # 正则表达式匹配图片,匹配bing搜索

        # 响应头,假装我是浏览器访问的网页
        headers ={'User-Agent':UserAgent().random}
        urllib3.disable_warnings()                         #忽略警告
        response = requests.get(baseurl, headers=headers)  # 获取网页信息

        html = response.text                  # 将网页信息转化为text形式
        data=re.findall(ImgUrlPattern, html)  # 得到图片超链接的列表
        return data                           # 返回一个包含该页面全部图片超链接的新列表

    '''
    函数功能:
        遍历输入的图像urls
        并将其下载下来
    '''
    def DownloadImg(self,imgUrls):

        # 头,假装我是浏览器访问的网页
        headers={'User-Agent':UserAgent().random}
        for ImgUrl in imgUrls:
            if self.Dowdnum < self.imgNum:  #判断次数是否够了
                # 如果url是无效的,则查看下一个url
                try:
                    resp = requests.get(ImgUrl, headers=headers)    # 获取网页信息
                except requests.ConnectionError as e:
                    continue
                byte = resp.content                                 # 转化为content二进制
                with open("{:0>5d}.jpg".format(self.Dowdnum + 1), "wb") as f:  # 文件写入
                    if resp.status_code==200 and len(str(byte)) > 1000 :  # 访问成功200且返回页面字节长度大于1000
                        f.write(byte)
                        # print(len(str(byte)))
                        self.Dowdnum = self.Dowdnum + 1        # 递增,表示又多下载了一张图片
                        time.sleep(0.5)  # 每隔0.5秒下载一张图片,避免由于访问过快被反爬了,认为我在DDS攻击服务器
                        print("第{}张与{}有关的图片爬取成功!".format(self.Dowdnum, self.search))
            else:
                break





    def run(self):

        while(self.Dowdnum<self.imgNum):
            for index in range(10000):#预估一个最大页数,不可能超过这个页数的
                if self.engine=='baidu':
                    decteUrl=self.dicUrl[self.engine].format(parse.quote(self.search),parse.quote(self.search),index*30,str(int(time.time()*1000)))
                elif self.engine=='bing':
                    decteUrl=self.dicUrl[self.engine].format(self.search,index*35) #dicUrl保存着 引擎与搜索地址的映射
                imgUrls=self.geturls(decteUrl,self.dicPattern[self.engine])        #获取网页中所有图片地址
                self.DownloadImg(imgUrls)                                #输入地址,开始下载
                if self.Dowdnum>=self.imgNum:
                    break
        if(self.Dowdnum==self.imgNum):
            print("已基于搜索引擎{}爬取了{}张与{}相关的图片,保存在文件夹{}".format(self.engine,self.imgNum,self.search,os.getcwd()))
    engine='bing'
    def ImgGenerate(search,imgNum,File):
        pass
    def setOutFile(self,outFile):
        self.outFile=outFile

def main():
    print('有效的引擎有:bing,baidu')
    engine = input('请输入引擎:')  # 要爬取的引擎,有效值有:bing,baidu
    search = input('请输入检索词:')  # 检索词
    imgNum = int(input('请输入爬取图片数量:'))  # 爬取图片数量

    outFile=os.getcwd()


    ImgG = ImgGenerate(engine,search,imgNum,outFile)
    ImgG.run()


if __name__ == '__main__':
    main()

四、完结撒花

1、运行截图

在这里插入图片描述
运行如上
还缺一个基于MD5码的图片自动去重。这个我在软件,以及随后的github中再添加了

2、自动爬取图片的软件

图片爬虫到这里就结束了
我准备开发一个爬虫软件,到时候会放在着,就不需要配环境了
等我两天好吧,效率
我先去学Qt

五、补充

1、下载原图设计过程

注:由于直接在搜索引擎上下载的图片,都经过了搜索引擎的压缩,模糊,每张大小10k左右,这样很明显不能很好的满足我们的需求。
为此我们需要加一步,进去然后再加载
大体步骤跟上面差不多。下载网页源码,进行分析,然后找出特性,进去再加载即可

a、如何在bing源码中直接下载原图

在这里插入图片描述
慢慢看网页源码可以找到如上,地址映射,我们要的是直接下载原图也就是murl后面的的地址,我找了30多分钟,有点忧伤,应该是不熟练的缘故:https://img.zcool.cn/community/016f405d2b3735a80120b5ab031177.jpg@1280w_1l_2o_100sh.jpg
这个就是我们要的。

获取信息分析如下:

  • bing真正下载原图的正则表达式:
  • murl&quot;:&quot;(.*?)&
    将这个模式,替换掉原来的即可

    b、如何在baidu源码中直接下载原图

在这里插入图片描述获取信息分析如下:

  • baidu真正下载原图的正则表达式:
  • "thumbURL":"(.*?)"
    将这个模式,替换掉原来的即可

2、源码

#coding=utf-8
import re
import time
import requests
from urllib import parse #对汉字进行编码
import os
#用来随机抽头发出申请

from fake_useragent import UserAgent #随机生成一个user-agent,模拟有多个浏览器访问
#import urllib3

class ImgGenerate:
    def __init__(self,engine,search,maxNum,outFile):

        self.dicPattern={'bing':r'<img class="mimg vi.*src="(.*?)"','baidu':r'"middleURL":"(.*?)"'} #下载小图匹配的正则表达式
        self.dicPatternEr = {'bing': r'murl&quot;:&quot;(.*?)&', 'baidu': r'"thumbURL":"(.*?)"'}   #下载原图匹配的正则表达式
        self.dicUrl={'bing':'https://cn.bing.com/images/search?q={}&form=HDRSC2&first={}&tsc=ImageHoverTitle','baidu':'https://image.baidu.com/search/acjson?tn=resultjson_com&logid=7542812996841482750&ipn=rj&ct=201326592&is=&fp=result&fr=&word={}&queryWord={}&cl=2&lm=-1&ie=utf-8&oe=utf-8&adpicid=&st=-1&z=&ic=0&hd=&latest=&copyright=&s=&se=&tab=&width=&height=&face=0&istype=2&qc=&nc=1&expermode=&nojc=&isAsync=&pn={}&rn=30&gsm=1e&{}='}
        self.engine = engine  #检索引擎
        self.search =search   #检索词
        self.Dowdnum=0        #当前已经下载数量
        self.imgNum =maxNum   #下载数量
        self.outFile=outFile  #下载图片的地址

        try:
            # 确保当前目录位于search目录,图片将保存在这一目录
            os.chdir(self.outFile)

            if not os.path.isdir("./{}_{}".format(search,engine)):  # 确定文件夹一定存在
                os.mkdir("./{}_{}".format(search,engine))
            os.chdir("./{}_{}".format(search,engine))
        except:
            print("请输入正常的检索词")

    '''
    函数功能
        输入一个地址和,网页源码,
        将源码写入txt文本,便于浏览
    '''
    def writeHtml(self,outfile,html):
        with open(outfile,'w',encoding='utf-8') as f:
            f.write(str(html))

    '''
    函数功能
        返回一个url页面里面全部图片超链接的列表
    '''
    def geturls(self,baseurl,enginPattern):
        ImgUrlPattern = re.compile(enginPattern)  # 正则表达式匹配图片,匹配bing搜索

        # 响应头,假装我是浏览器访问的网页
        headers ={'User-Agent':UserAgent().random}
        #urllib3.disable_warnings()                         #忽略警告
        response = requests.get(baseurl, headers=headers)  # 获取网页信息

        html = response.text                  # 将网页信息转化为text形式
        data=re.findall(ImgUrlPattern, html)  # 得到图片超链接的列表
        return data                           # 返回一个包含该页面全部图片超链接的新列表

    '''
    函数功能:
        遍历输入的图像urls
        并将其下载下来
    '''
    def DownloadImg(self,imgUrls):

        # 头,假装我是浏览器访问的网页
        headers={'User-Agent':UserAgent().random}
        for ImgUrl in imgUrls:
            if self.Dowdnum < self.imgNum:  #判断次数是否够了
                # 如果url是无效的,则查看下一个url
                try:
                    resp = requests.get(ImgUrl, headers=headers)    # 获取网页信息
                except requests.ConnectionError as e:
                    continue
                byte = resp.content                                 # 转化为content二进制
                with open("{:0>5d}.jpg".format(self.Dowdnum + 1), "wb") as f:  # 文件写入
                    if resp.status_code==200 and len(str(byte)) > 1000 :  # 访问成功200且返回页面字节长度大于1000
                        f.write(byte)
                        # print(len(str(byte)))
                        self.Dowdnum = self.Dowdnum + 1        # 递增,表示又多下载了一张图片
                        time.sleep(0.5)  # 每隔0.5秒下载一张图片,避免由于访问过快被反爬了,认为我在DDS攻击服务器
                        print("第{}张与{}有关的图片爬取成功!".format(self.Dowdnum, self.search))
            else:
                break





    def run(self):

        while(self.Dowdnum<self.imgNum):
            for index in range(10000):#预估一个最大页数,不可能超过这个页数的
                if self.engine=='baidu':
                    decteUrl=self.dicUrl[self.engine].format(parse.quote(self.search),parse.quote(self.search),index*30,str(int(time.time()*1000)))
                elif self.engine=='bing':
                    decteUrl=self.dicUrl[self.engine].format(self.search,index*35) #dicUrl保存着 引擎与搜索地址的映射
                imgUrls=self.geturls(decteUrl,self.dicPatternEr[self.engine])        #获取网页中所有图片地址
                self.DownloadImg(imgUrls)                                #输入地址,开始下载
                if self.Dowdnum>=self.imgNum:
                    break
        if(self.Dowdnum==self.imgNum):
            print("已基于搜索引擎{}爬取了{}张与{}相关的图片,保存在文件夹{}".format(self.engine,self.imgNum,self.search,os.getcwd()))
    engine='bing'
    def ImgGenerate(search,imgNum,File):
        pass
    def setOutFile(self,outFile):
        self.outFile=outFile

def Down_One_Img(url):
    header={'User-Agent':UserAgent().random}

    html=requests.get(url,headers=header).content
    print(os.getcwd())
    with open('../Images/10001.jpg','wb')as w:
        w.write(html)
def main():
    print('有效的引擎有:bing,baidu')
    engine = input('请输入引擎:')  # 要爬取的引擎,有效值有:bing,baidu
    search = input('请输入检索词:')  # 检索词
    imgNum = int(input('请输入爬取图片数量:'))  # 爬取图片数量

    outFile=os.getcwd()


    ImgG = ImgGenerate(engine,search,imgNum,outFile)
    ImgG.run()


if __name__ == '__main__':
   # ImgGen=ImgGenerate('bing','im1',23,'images')
    #url='https://img0.baidu.com/it/u=3965453168,289903526&fm=253&fmt=auto&app=138&f=JPEG?w=667&h=500'
    #Down_One_Img(url)
    main()

六、图片爬虫软件exe下载与全部源码开源GitHub地址

在开发了最迟明天好伐

  Python知识库 最新文章
Python中String模块
【Python】 14-CVS文件操作
python的panda库读写文件
使用Nordic的nrf52840实现蓝牙DFU过程
【Python学习记录】numpy数组用法整理
Python学习笔记
python字符串和列表
python如何从txt文件中解析出有效的数据
Python编程从入门到实践自学/3.1-3.2
python变量
上一篇文章      下一篇文章      查看所有文章
加:2022-07-17 16:19:02  更:2022-07-17 16:20:03 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/15 11:49:41-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码