Python爬虫获取百度的图片

一. 爬虫的方式:

主要有2种方式:

①Scrapy+Xpath  (API 静态 爬取-直接post get) 

②selenium+Xpath (点击 动态 爬取-模拟) 

Scrapy+Xpath  

XPath 是 Scrapy 中常用的一种解析器,可以帮助爬虫定位和提取 HTML 或 XML 文档中的数据。

Scrapy 中使用 XPath 的方式和普通的 Python 程序基本一致。我们需要首先导入 scrapy 的 Selector 类和 scrapy 的 Request 类,然后使用 Selector 类来解析 Response 对象,并使用 XPath 表达式来定位和提取数据。

详细讲解可以参考:Scrapy爬虫学习笔记之二(Xpath的用法) - 知乎

selenium+Xpath

Selenium 是为了解决 requests 无法直接执行 JavaScript 代码的问题。本质是通过驱动浏览器,完全模拟浏览器的操作,输入、点击、下拉等。

安装:pip install selenium

使用需要下载浏览器驱动,并且驱动要跟浏览器版本对应

chrome浏览器版本在114之前

浏览器版本在114之前,可以进入以下网址http://chromedriver.storage.googleapis.com/index.html,直接下载相应的文件

chrome浏览器版本在115以上

以下版本皆为chromedriver版本

例如:version : 119.0.6045.21,你电脑的浏览器版本为其他版本,如118.0.5952.2,只需要把链接中的版本号替换成这个编号即可

平台下载地址
linux64http:// https://edgedl.me.gvt1.com/edgedl/chrome/chrome-for-testing/119.0.6045.21/linux64/chromedriver-linux64.zip
mac-arm64https://edgedl.me.gvt1.com/edgedl/chrome/chrome-for-testing/119.0.6045.21/mac-arm64/chromedriver-mac-arm64.zip
mac-x64https://edgedl.me.gvt1.com/edgedl/chrome/chrome-for-testing/119.0.6045.21/mac-x64/chromedriver-mac-x64.zip
win32https://edgedl.me.gvt1.com/edgedl/chrome/chrome-for-testing/119.0.6045.21/win32/chromedriver-win32.zip
win64https://edgedl.me.gvt1.com/edgedl/chrome/chrome-for-testing/119.0.6045.21/win64/chromedriver-win64.zip

Chromedriver 插件安装教程

参考:稳扎稳打学爬虫09—chromedriver下载与安装方法-CSDN博客

下面简单使用模拟百度搜索:

import time

from selenium import webdriver

bro = webdriver.Chrome(executable_path='./chromedriver.exe')  # 得到一个谷歌浏览器对象,并指定使用那个驱动

bro.implicitly_wait(5)  # 隐士等待:找一个控件,如果控件没有加载出来,就等待5S,只需要写着一句,以后所有控件都按照这个操作来

bro.get('https://www.baidu.com')  # 在地址栏里输入百度

input_k = bro.find_element_by_id('kw')  # 找到百度输入框对应的控件

input_k.send_keys('火灾火焰')  # 框里面输入python

sou = bro.find_element_by_id('su')  # 找到搜索按钮

sou.click()  # 点击搜索按钮

time.sleep(3)

bro.close()  # 关闭浏览器

selenium详细用法参考:https://www.cnblogs.com/XiaoYang-sir/p/15173174.html

二. selenium+xpath

利用selenium获取元素定位方法,爬取百度图片

通过定位获取完整爬取图片的超链接信息,鼠标放置百度页面右键=》检测

完整爬取代码

'''

注释:
    @author is leilei
    百度图片爬虫,采用selenium模拟鼠标点击形式
    1. 将要搜索的文本表示成list
    2. 打开百度图片官网,输入文本,搜索
    3. 逐条下载对应的图片
注:
    本代码支持断点续爬!
'''

import os
import uuid
import time
import random
import urllib
import urllib.request
from selenium import webdriver
from selenium.webdriver.common.keys import Keys  # 键盘类


#爬取的种类图片
NameList=['火灾火焰', '火灾烟雾']

def send_param_to_baidu(name, browser):
    '''
    :param name:    str
    :param browser: webdriver.Chrome 实际应该是全局变量的
    :return:        将要输入的 关键字 输入百度图片
    '''
    # 采用id进行xpath选择,id一般唯一
    inputs = browser.find_element_by_xpath('//input[@id="kw"]')
    inputs.clear()
    inputs.send_keys(name)
    time.sleep(1)
    inputs.send_keys(Keys.ENTER)
    time.sleep(1)

    return

'''
写Python爬虫的时候,没过多久Python就会报错,然后停止采集。总是没办法从头到尾把数据采集下来。
每一下次报错我都要去找原因,比如我要采集的标签里面没有URL,URL为空就会报错,
或者页面没有URL也会报错。于是我是用try…except语句跳过错误,但是还是会遇到其他问题,
就是try…except语句只能跳过一次错误,第二次错误就会失效。所以采用了下面这种mistaken方法处理异常。
'''
def mistaken():
	try:
		print('*****出现异常错误,跳过此次循环,爬取无内容*****')
		######采集代码##########
		print('——————————接下来继续运行——————————')
	except:
		mistaken()

def download_baidu_images(save_path, img_num, browser):
    ''' 此函数应在
    :param save_path: 下载路径 str
    :param img_num:   下载图片数量 int
    :param name:   爬取种类的名字
    :param browser:   webdriver.Chrome
    :return:
    '''
    if not os.path.exists(save_path):
        os.makedirs(save_path)

    ##下面是打开第一张图片,然后在此界面中点击左右切换图片
    # // *[ @ id = "imgid"]/div[1]/ul/li[1]/div/div[2]/a/img
    #如果这里报错,其中下面这里的定位地址,需要根据百度你爬取的图片的位置进行相应的修改
    img_link = browser.find_element_by_xpath(' //*[@id = "imgid"]/div[1]/ul/li[1]/div/div[2]/a/img')
    img_link.click()

    # 切换窗口
    windows = browser.window_handles
    browser.switch_to.window(windows[-1])  #切换到图像界面
    # time.sleep(3)
    time.sleep(random.random())

    for i in range(img_num):
        img_link_ = browser.find_element_by_xpath('//div/img[@class="currentImg"]')
        src_link = img_link_.get_attribute('src')
        print(src_link)
        # 保存图片,使用urlib
        img_name = uuid.uuid4()
        # urllib.request.urlretrieve(src_link, os.path.join(save_path, str(img_name) + '.jpg'))
        # 上述一行代码直接去访问资源会报403错误,排查发现可能是服务器开启了反爬虫,针对这种情况添加headers浏览器头,模拟人工访问网站行为:
        opener = urllib.request.build_opener()
        # 构建请求头列表每次随机选择一个
        ua_list = ['Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:102.0) Gecko/20100101 Firefox/102.0',
                   'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.0.0 Safari/537.36',
                   'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.5060.114 Safari/537.36 Edg/103.0.1264.62',
                   'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:98.0) Gecko/20100101 Firefox/98.0',
                   'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3626.81 Safari/537.36 SE 2.X MetaSr 1.0'
                   ]
        opener.addheaders = [('User-Agent', random.choice(ua_list))]
        urllib.request.install_opener(opener)

        #为了不中断程序完整爬取,所以处理爬虫的过程中出现资源请求不到的错误404 或者403的错误,只需要跳过这些错误继续执行
        try:
            urllib.request.urlretrieve(src_link, os.path.join(save_path, str(img_name) + '.jpg'))
        except Exception as e:
            print(e)
            mistaken()


        # 如果网站反爬虫级别特别高的,还需要切换代理ip:使用urllib模块设置代理IP是比较简单的,首先需要创建ProxyHandler对象,其参数为字典类型的代理IP,键名为协议类型(如HTTP或者HTTPS),值为代理链接。然后利用ProxyHandler对象与buildopener()
        # 方法构建一个新的opener对象,最后再发送网络请求即可。
        # 创建代理IP
        # proxy_handler = urllib.request.ProxyHandler({
        #     'https': '58.220.95.114:10053'
        # })
        # # 创建opener对象
        # opener = urllib.request.build_opener(proxy_handler)


        # 关闭图像界面,并切换到外观界面
        time.sleep(random.random())

        # 点击下一张图片
        browser.find_element_by_xpath('//span[@class="img-next"]').click()
        time.sleep(random.random())

    # 关闭当前窗口,并选择之前的窗口
    browser.close()
    browser.switch_to.window(windows[0])

    return


def main(names, save_root, img_num=[1000, ], continue_num=0, is_open_chrome=True):
    '''
    :param names: list str
    :param save_root: str
    :param img_num: int list or int
    :param continue_num: int 断点续爬开始索引,从哪一个种类继续爬取
    :param is_open_chrome: 爬虫是否打开浏览器爬取图像 bool default=False
    :return:
    '''
    options = webdriver.ChromeOptions()
    # 设置是否打开浏览器
    if not is_open_chrome:
        options.add_argument('--headless')  # 不打开浏览器
    # else:
    #     prefs = {"profile.managed_default_content_settings.images": 2}  # 禁止图像加载
    #     options.add_experimental_option("prefs", prefs)

    # 欺骗反爬虫,浏览器可以打开,但是没有内容
    options.add_argument("--disable-blink-features=AutomationControlled")
    browser = webdriver.Chrome(executable_path=r"D:\Anconda\envs\temp\Lib\site-packages\selenium\webdriver\chrome\chromedriver.exe",options=options)
    browser.maximize_window()
    browser.get(r'https://image.baidu.com/')
    time.sleep(random.random())


    assert type(names) == list, "names参数必须是字符串列表"
    assert continue_num <= len(names), "中断续爬点需要小于爬虫任务数量"

    if type(img_num) == int:
        img_num = [img_num] * len(names)
        print(img_num)
    elif type(img_num) == list:
        print("lsit:{}".format(img_num))
    else:
        print("None, img_num 必须是int list or int")
        return

    for i in range(continue_num, len(names)):
        name = names[i]
        save_path = os.path.join(save_root, str(names.index(name)))  # 以索引作为文件夹名称
        send_param_to_baidu(name, browser)
        download_baidu_images(save_path=save_path, img_num=img_num[i],browser=browser)
    # 全部关闭
    browser.quit()
    return


if __name__ == "__main__":
    main(names=NameList,save_root=r'C:\Users\HUAWEI\Desktop\photo',img_num=[1000, 1000],continue_num=1)

具体selenium的动态定位法:

参考链接: https://blog.csdn.net/u012206617/article/details/132451577?utm_medium=distribute.pc_relevant.none-task-blog-2~default~baidujs_baidulandingword~default-0-132451577-blog-109838581.235^v40^pc_relevant_anti_vip&spm=1001.2101.3001.4242.1&utm_relevant_index=3

 三. Scrapy+Xpath  

 需要使用 icrawler 包   [ps:直接pip install icrawler]

完整的代码1:

import os
from icrawler.builtin import BaiduImageCrawler
from icrawler.builtin import BingImageCrawler

#可以使用,使用icrawler包静态爬取图片

def check_path(path):
    if not os.path.exists(path):
        os.makedirs(path)
    return path

def baidu_bing_crwal(key_words=['中国人'], max_nums=[1000], save_root=r'./'):
    #看是否存在文件夹
    check_path(save_root)

    assert len(key_words)==len(max_nums), "关键词和数量必须一致"
    # 2个一起爬虫
    save_root1 = os.path.join(save_root, 'baidu')
    # 百度爬虫
    for i in range(len(key_words)):
        print('-'*20)
        image_save_root = os.path.join(save_root1, str(i))

        if not os.path.exists(image_save_root):
            os.makedirs(image_save_root)

        storage = {'root_dir': image_save_root}
        crawler = BaiduImageCrawler(storage=storage)
        crawler.crawl(key_words[i], max_num=max_nums[i])

    # bing爬虫
    save_root2 = os.path.join(save_root, 'bing')
    for i in range(len(key_words)):
        print('-'*20)
        image_save_root = os.path.join(save_root2, str(i))

        if not os.path.exists(image_save_root):
            os.makedirs(image_save_root)

        storage = {'root_dir': image_save_root}
        crawler = BingImageCrawler(storage=storage)

        crawler.crawl(key_words[i], max_num=max_nums[i])
    return

if __name__ == '__main__':
    # baidu_bing_crwal(key_words=['生活垃圾', '化学垃圾',],
    #                  max_nums=[1000, 1000],
    #                  save_root=r'C:\Users\HUAWEI\Desktop\photo\da')
    baidu_bing_crwal(key_words=['火灾火焰', '火灾烟雾'],
                     max_nums=[1000, 1000],
                     save_root=r'C:\Users\HUAWEI\Desktop\photo\da')

 其实简化的静态爬虫方式

完整的代码2:

'''
    底层肯定是scrapy静态报文,谷歌引擎不可以,百度最快,bing速度有点慢!
    直接pip install icrawler
    
    若想搜索多个关键词,可以遍历for循环;同时icrawler也可对图像链接list、txt直接遍历:
    UrlListCrawler
'''
from icrawler.builtin import GoogleImageCrawler
from icrawler.builtin import BaiduImageCrawler
from icrawler.builtin import BingImageCrawler

# storage字典格式'root_dir': 保存路径
# crawler = BaiduImageCrawler(storage={'root_dir': r'D:\temp\dog'})
crawler = BaiduImageCrawler(storage={'root_dir': r'C:\Users\HUAWEI\Desktop\photo'})
crawler.crawl(keyword='火焰', max_num=10)

最后:爬取图片的任务完成了 ,☺☺☺

学习参考链接:python 爬虫_python爬虫断点续爬-CSDN博客

 稳扎稳打学爬虫09—chromedriver下载与安装方法-CSDN博客

爬虫selenium获取百度任意图片_img_link = browser.find_elements_by_xpath('//li/di-CSDN博客Python爬虫:爬取百度图片(selenium模拟登录,详细注释)_百度图片 爬虫 find_elements-CSDN博客

爬虫selenium获取元素定位方法总结(动态获取元素)_selenium如何定位动态元素-CSDN博客

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/299942.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

大学物理实验重点——偏振光与双折射

线偏振光、椭圆偏振光、圆偏振光均可由两个频率相同、振动方向垂直、位相差恒定的线偏振光合成。 单轴晶体中&#xff0c;若其 o 光折射率大于 e 光折射率&#xff0c;也即 o 光传播速度小于 e 光传播速度&#xff0c;称之为负晶体&#xff0c;反之为正晶体。 o光和e光…

#error 在C语言中的作用

1、#error命令是C/C语言的预处理命令之一 #error 是C语言中的预处理指令之一&#xff0c;用于在编译时生成一个错误消息。当编译器遇到 #error 指令时&#xff0c;会立即停止编译&#xff0c;并将指定的错误消息输出到编译器的错误信息中。 在给定的代码中&#xff0c;#error…

2.6 KERNEL LAUNCH

图2.15在vecAdd函数中显示最终主机代码。此源代码完成了图2.6.中的骨架。2.12和2.15共同说明了一个简单的CUDA程序&#xff0c;该程序由主机代码和设备内核组成。该代码是硬接的&#xff0c;每个线程块使用256个线程。然而&#xff0c;使用的线程块的数量取决于向量&#xff08…

元数据管理平台对比预研 Atlas VS Datahub VS Openmetadata

大家好&#xff0c;我是独孤风。元数据管理平台层出不穷&#xff0c;但目前主流的还是Atlas、Datahub、Openmetadata三家&#xff0c;那么我们该如何选择呢&#xff1f; 本文就带大家对比一下,这三个平台优势劣势。要了解元数据管理平台&#xff0c;先要从架构说起。 正文共&am…

基因组学之碱基突变的关键概念

碱基突变 突变&#xff08;muation&#xff09;会引起DNA序列的变化&#xff0c;进一步会引起蛋白序列的改变。正常的细胞活动或细胞与环境的随机相互作用&#xff0c;会使得生物产生一定数目的突变&#xff0c;称为自发突变&#xff08;spontaneous muation&#xff09;。突变…

Qt6入门教程 4:Qt Creator常用技巧

在上一篇Qt6入门教程 3&#xff1a;创建Hello World项目中&#xff0c;通过创建一个Qt项目&#xff0c;对Qt Creator已经有了比较直观的认识&#xff0c;本文将介绍它的一些常用技巧。 Qt Creator启动后默认显示欢迎页面 创建项目已经用过了&#xff0c;打开项目也很简单&#…

毛概笔记。

一、 毛泽东思想是马中化的第一果&#xff0c;是关于搞革命&#xff0c;搞改造&#xff0c;搞建设的理论。 二、新民主主义革命 新民主主义革命的三大法宝&#xff1a;1.统一战线 2. 武装斗争 3.党的建设 政治纲领 经济纲领 文化纲领 乱世造英雄 三、社会主义改造理论&#xff…

Mac/Window 如何下载安装 Pycharm 2023

文章目录 1. 下载 Pycharm2. jiebra 工具下载3. jiebra 工具安装3.1 Window 端3.2 Mac 端 1. 下载 Pycharm Pycharm 下载官网&#xff0c;可以下载的是最新版的 Pycharm&#xff0c;但不保证可以jihuo&#xff1b; 如果需要保证可用的&#xff0c;建议直接下载资源&#xff…

猫主食冻干品牌k9、sc、希喂!哪款主食冻干才是布偶猫的最爱?

提到布偶猫的喂养问题&#xff0c;真的是让很多铲屎官头疼不已啊&#xff01;这小家伙虽然是食肉动物&#xff0c;但由于肠胃脆弱敏感&#xff0c;所以在饮食上得特别注意哦&#xff01;好消息是&#xff0c;现在有了主食冻干这种好东西&#xff01;它不仅贴合猫咪的天然饮食习…

Winform中使用Websocket4Net实现Websocket客户端并定时存储接收数据到SQLite中

场景 SpringBootVue整合WebSocket实现前后端消息推送&#xff1a; SpringBootVue整合WebSocket实现前后端消息推送_websocket vue3.0 springboot 往客户端推送-CSDN博客 上面实现ws推送数据流程后&#xff0c;需要在windows上使用ws客户端定时记录收到的数据到文件中&#x…

SRv6简介

文章目录 SR&#xff0c;分段路由IPv6 SRv6&#xff0c;简单来理解&#xff0c;其实就是 SRIPv6。 SRv6(Segment Routing v6&#xff0c;基于IPv6转发平面的段路由)是基于源路由理念而设计的在网络上转发数据包的一种协议。其核心思想是将报文转发路径切割成不同的段&#xff…

[Linux c/c++] 关于进程名,线程名,/proc文件系统 等

参考&#xff1a; kernel - Why is the name of a process in /proc/PID/status not matching package name or ps command - Stack Overflowhttps://stackoverflow.com/questions/14176058/why-is-the-name-of-a-process-in-proc-pid-status-not-matching-package-name-or-ps…

Opencv与PyQt5设计一个摄像头界面

一、前言 本篇的内容是学习的这一位博主的&#xff1a;程序界面设计_Doc_Cheng的博客-CSDN博客。 这是我见过很详细的教你如何使用的PyQt5来完成UI界面设计的&#xff0c;专注于UI界面设计。对我而言&#xff0c;这教程就像是一个实用工具&#xff0c;因为我只需要能够显示图…

MySQL之视图案例

目录 一.视图1.1 含义1.2 操作 二.案例三.思维导图 一.视图 1.1 含义 虚拟表&#xff0c;和普通表一样使用 1.2 操作 1.创建视图 create view 视图名 as 查询语句&#xff1b; 2.视图的修改 方式一&#xff1a; create or replace view 视图名 as 查询语句 方式二&#x…

H266/VVC率失真优化概述

率失真优化技术 率失真优化&#xff1a; 视频编码的主要目的是在保证一定视频质量的条件下尽量降低视频的编码比特率&#xff0c;或者在一定编码比特率限制条件下尽量地减小编码失真。在固定的编码框架下&#xff0c;为了应对不同的视频内容&#xff0c;往往有多种候选的编码方…

国标28181平台 管理下级推送来的目录资源

目 录 一、业务分组目录和行政区划目录的定义 &#xff08;一&#xff09;业务分组目录 &#xff08;二&#xff09;行政区划目录 &#xff08;三&#xff09;实际应用的目录结构 二、国标28181支持目录资源的推送 三、支持国标28181的视频监控平台…

爬虫-3-模拟登录,代理ip,json模块

#本文仅供学习使用(O&#xff40;) 如果服务器响应的数据为json数据: 那么我们可以用 res.json() 或 json模块(将json字符串转换为Python里面的字典类型) 接收数据。

关于java的多维数组

关于java的多维数组 在前面的文章中&#xff0c;我们了解了数组的使用&#xff0c;我们之前所了解的数组是一维数组&#xff0c;本篇文章我们来了解一下二维数组&#xff0c;多维数组&#x1f600; 一、二维数组 首先我们知道一维数组的声明和创建的方式是。 int array ne…

Java面试——框架篇

1、Spring框架中的单例bean是线程安全的吗&#xff1f; 所谓单例就是所有的请求都用一个对象来处理&#xff0c;而多例则指每个请求用一个新的对象来处理。 结论&#xff1a;线程不安全。 Spring框架中有一个Scope注解&#xff0c;默认的值就是singleton&#xff0c;单例的。一…

[算法应用]dijkstra算法的应用

先看一眼原始dijkstra算法&#xff0c;参考自dijkstra算法C实现_c实现djikstra-CSDN博客 分为三步 找到当前最优的把当前最优的&#xff0c;不参与后面的更新逐个比较是否更新 dijkstra算法的应用 题目大概是要从图上找一条权值不减的路径&#xff0c;且要经过最多的点。 所以…