和我一起学Python,一起采集妹子图

目录

  • 推荐
  • 一、小小课堂
  • 二、保存内容成html
  • 2.1 通过selenium模拟普通人查找百度图片1. 普通人搜索图片2 分析3 代码实现4 模拟人为鼠标滑轮滚动屏幕2.2 此部分完整代码2.3 保存HTML并查看是否保存成功
  • 三、解析图片链接
  • 3.1 前期分析3.2 正则提取URL
  • 四、完整代码
  • 五、爬取结果
  • 六、修改版源码(加上代理IP)

很多人学习python,不知道从何学起。
很多人学习python,掌握了基本语法过后,不知道在哪里寻找案例上手。
很多已经做案例的人,却不知道如何去学习更加高深的知识。
那么针对这三类人,我给大家提供一个好的学习平台,免费领取视频教程,电子书籍,以及课程的源代码!??¤
QQ群:961562169

一、小小课堂

经过上篇的简单介绍,相信你们已经对selenium有了初步的了解,那么!为了让大家对selenium有进一步的了解。细心的博主给大家带来了福利,那就是使用selenium爬取百度妹子图。希望大家不要叫我LSP!


至于通过怎样的思路爬取百度妹子图呢?博主的大体思路是先获取一定量的内容保存成html页面,然后通过解析已经保存的html中的图片链接,然后保存到本地。

二、保存内容成html

2.1 通过selenium模拟普通人查找百度图片

1. 普通人搜索图片


已知,正常人打开百度导航搜索图片的正确方式应该是这样的:百度导航—>输入关键词—》点击查找—》点击所有图片

2 分析

🆗知道了普通人如何查找图片,那么我们下面就通过selenium模拟上述的具体过程。在模拟之前,我们先分析一下几个主要的点。

 

  •  1. 输入框
    我们通过打开开发者选项,找到输入框所在部分,解析xpath
     
  •  2. 查询点击
     
  •  3. 点击关于美女的百度图片
     

3 代码实现

    # 控制chrome浏览器
    driver = webdriver.Chrome("./chromedriver/chromedriver.exe")
    #窗口最大化
    driver.maximize_window()
    # 输入网址
    driver.get("https://www.baidu.com/")
    # 找到文本框,输入文字
    driver.find_element_by_xpath('//*[@id="kw"]').send_keys("哆啦a梦图片")
    #找到按钮,单击
    driver.find_element_by_xpath('//*[@id="su"]').click()
    #停一下,等待加载完毕
    time.sleep(2)

    #找到a标签,单击
    driver.find_element_by_xpath('//*[@id="1"]/h3/a').click()
    #停一下,等待加载完毕
    time.sleep(2)


🆗,我们可以看到已经完美的模拟出来过程。

window.scrollTo(0,10000)


在这里我们看效果是很不错的,但是其实还是有点小问题的,我们现在其实还只是在第一个窗口中,因此我们需要切换一下的窗口,这个时候我们就需要添加下面一行代码

#切换窗口,因为现在打开了一个窗口,目前还是在第1个窗口中
driver.switch_to.window(driver.window_handles[1])

4 模拟人为鼠标滑轮滚动屏幕

模拟人为鼠标滑轮滚动屏幕,我们有Selenium+python自动化之js屏幕滑动,下列为脚本实现js滑屏

scroll="document.documentElement.scrollTop=800"#垂直滚动 px
scroll = "document.documentElement.scrollLeft=1000"#水平滚动
scroll="window.scrollTo(0,10000)"#滚动到指定坐标
scroll="window.scrollBy(0,100)"#滑动到相对坐标
scroll="window.scrollTo(0,document.body.scrollHeight)"#获取body的高度,滑到底部
document.body.scrollWidth 获取body宽度
driver.execute_script(scroll)

在此,博主使用了滑动到指定坐标。由于已经验证过了,所以直接给出正确游标

window.scrollTo(0,10000)

效果图如下:


在此,博主先测试翻页10次,代码如下

    for i in range(10):
        #执行js
        driver.execute_script("window.scrollTo(0,10000)")
        time.sleep(1)

效果图:


好了,所有的准备工作,我们已经完成了。那么接下来我们只需把他保存为html页面即可。

2.2 此部分完整代码

from selenium import webdriver
from lxml import etree
import os
import time
import requests
import re
import random

headers = {
    "user-agent": "Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/55.0.2883.87 Safari/537.36",
}

#创建文件夹
if not os.path.exists("./files/baidu"):
    os.makedirs("./files/baidu")


def get_html():
    # 控制chrome浏览器
    driver = webdriver.Chrome("./chromedriver/chromedriver.exe")
    #窗口最大化
    driver.maximize_window()
    # 输入网址
    driver.get("https://www.baidu.com/")
    # 找到文本框,输入文字
    driver.find_element_by_xpath('//*[@id="kw"]').send_keys("哆啦a梦图片")
    #找到按钮,单击
    driver.find_element_by_xpath('//*[@id="su"]').click()
    #停一下,等待加载完毕
    time.sleep(2)

    #找到a标签,单击
    driver.find_element_by_xpath('//*[@id="1"]/h3/a').click()
    #停一下,等待加载完毕
    time.sleep(2)
    #切换窗口,因为现在打开了一个窗口,目前还是在第1个窗口中
    driver.switch_to.window(driver.window_handles[1])
    for i in range(10):
        #执行js
        driver.execute_script("window.scrollTo(0,10000)")
        time.sleep(1)
    #获取页面html
    html = driver.page_source
    # 关闭
    driver.quit()
    #保存html
    with open("baidu.html","w",encoding="utf-8") as file:
        file.write(html)

    return html

if __name__ == '__main__':
    get_html()

2.3 保存HTML并查看是否保存成功

 


到这里,我们的保存工作就已经完成了,下面就需要对其进行解析了。

三、解析图片链接

3.1 前期分析

在此先给出所以能够爬取的图片URL,然后进行分析,如何得到

data-objurl="http://pic.jj20.com/up/allimg/1113/041620103S8/200416103S8-4-1200.jpg"
data-imgurl="https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=1948216838,2050876637&fm=26&gp=0.jpg">
"hoverURL":"https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=1948216838,2050876637&fm=26&gp=0.jpg"
"thumbURL":"https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=1672252528,4061027335&fm=26&gp=0.jpg"
"middleURL":"https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=1672252528,4061027335&fm=26&gp=0.jpg"

我们首先先把得到的html打印出来,然后通过查找URL,找到图片的URL即可

 


由于本次博主只以此两个URL为例,所以其他的都不在自行查找了。

在提取图片的URL之前,我们先查看下是不是我们所要的图片,随便打开一个
如:https://ss0.bdstatic.com/70cFuHSh_Q1YnxGkpoWK1HF6hhy/it/u=3026930057,3755157843&fm=26&gp=0.jpg


🆗,正是我们所需要的图片,下面就可以开始提取了。

3.2 正则提取URL

    #读数据
    with open("baidu.html", "r", encoding="utf-8") as file:
        html = file.read()
    #通过正则获取img url
    img_list1 = re.findall(r'data-objurl="(.*?)"', html)
    img_list2 = re.findall(r'data-imgurl="(.*?)"', html)
    #合并
    img_list1.extend(img_list2)
    print(img_list2)


现在我们先打开URL,看看能不能打开。


结果我们发现有的URL并不能打开,这是正常的,因为各种原因总会有某些URL无法打开,这时候我们先多找几个URL试验即可。


但是直接这样看的话,并不好看,这个时候我们需要把他遍历并打印所有的URL

    #替换部分不需要的字符
    img_list = map(lambda x:x.replace("amp;",""),img_list1)
    #遍历
    for img in img_list:
        print(img)
        time.sleep(random.random()*3)

然后查看结果


🆗,到这里我们所有需要分析的部分都已经分析完成了。

四、完整代码

# encoding: utf-8

from selenium import webdriver
from lxml import etree
import os
import time
import requests
import re
import random

headers = {
    "user-agent": "Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/55.0.2883.87 Safari/537.36",
}

#创建文件夹
if not os.path.exists("./files/baidu"):
    os.makedirs("./files/baidu")


def get_html():
    # 控制chrome浏览器
    driver = webdriver.Chrome("./chromedriver/chromedriver.exe")
    #窗口最大化
    driver.maximize_window()
    # 输入网址
    driver.get("https://www.baidu.com/")
    # 找到文本框,输入文字
    driver.find_element_by_xpath('//*[@id="kw"]').send_keys("美女")
    #找到按钮,单击
    driver.find_element_by_xpath('//*[@id="su"]').click()
    #停一下,等待加载完毕
    time.sleep(2)
    #找到a标签,单击
    driver.find_element_by_xpath('//*[@id="1"]/h3/a').click()
    #停一下,等待加载完毕
    time.sleep(2)
    #切换窗口,因为现在打开了一个窗口,目前还是在第1个窗口中
    driver.switch_to.window(driver.window_handles[1])
    for i in range(10):
        #执行js
        driver.execute_script("window.scrollTo(0,10000)")
        time.sleep(1)
    #获取页面html
    html = driver.page_source
    # 关闭
    driver.quit()
    #保存html
    with open("baidu.html","w",encoding="utf-8") as file:
        file.write(html)

    return html


def get_data():

    #读数据
    with open("baidu.html", "r", encoding="utf-8") as file:
        html = file.read()
    #通过正则获取img url
    img_list1 = re.findall(r'data-objurl="(.*?)"', html)
    img_list2 = re.findall(r'data-imgurl="(.*?)"', html)
    #合并
    img_list1.extend(img_list2)
    #替换部分不需要的字符
    img_list = map(lambda x:x.replace("amp;",""),img_list1)
    #遍历
    for img in img_list:
        print(img)
        time.sleep(random.random()*3)
        #获取图片字节,可能被拦截,加上代理ip
        content = requests.get(img,headers=headers).content
        #文件的名字
        filename = "./files/baidu/{}".format(img.split("/")[-1])
        #文件写
        with open(filename,"wb") as file:
            file.write(content)

if __name__ == '__main__':
    get_html()
    get_data()


# data-objurl="http://pic.jj20.com/up/allimg/1113/041620103S8/200416103S8-4-1200.jpg"
# data-imgurl="https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=1948216838,2050876637&fm=26&gp=0.jpg">
# "hoverURL":"https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=1948216838,2050876637&fm=26&gp=0.jpg"
# "thumbURL":"https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=1672252528,4061027335&fm=26&gp=0.jpg"
# "middleURL":"https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=1672252528,4061027335&fm=26&gp=0.jpg"

五、爬取结果

 


但是! 我们这样爬取的话,过一段时间就会被识别出来。如下图:


这个时候,我们最好加上代理IP 。进行循环爬取。

六、修改版源码(加上代理IP)

# encoding: utf-8

from selenium import webdriver
from lxml import etree
import os
import time
import requests
import re
import random

headers = {
    "user-agent": "Mozilla/5.0 (Windows NT 6.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/55.0.2883.87 Safari/537.36",
}

#创建文件夹
if not os.path.exists("./files/baidu"):
    os.makedirs("./files/baidu")


def get_html():
    # 控制chrome浏览器
    driver = webdriver.Chrome("./chromedriver/chromedriver.exe")
    #窗口最大化
    driver.maximize_window()
    # 输入网址
    driver.get("https://www.baidu.com/")
    # 找到文本框,输入文字
    driver.find_element_by_xpath('//*[@id="kw"]').send_keys("哆啦A梦图片")
    #找到按钮,单击
    driver.find_element_by_xpath('//*[@id="su"]').click()
    #停一下,等待加载完毕
    time.sleep(2)
    #找到a标签,单击
    driver.find_element_by_xpath('//*[@id="1"]/h3/a').click()
    #停一下,等待加载完毕
    time.sleep(2)
    #切换窗口,因为现在打开了一个窗口,目前还是在第1个窗口中
    driver.switch_to.window(driver.window_handles[1])
    for i in range(10):
        #执行js
        driver.execute_script("window.scrollTo(0,10000)")
        time.sleep(1)
    #获取页面html
    html = driver.page_source
    # 关闭
    driver.quit()
    #保存html
    with open("baidu.html","w",encoding="utf-8") as file:
        file.write(html)

    return html


def get_proxies():
    #这里获取的芝麻HTTP代理http https\\
    time.sleep(2+random.random()*3)
    proxies = {
        "http": "",
        "https": ""
    }
    url = "http://http.tiqu.alicdns.com/getip3?num=1&type=2&pro=&city=0&yys=0&port=11&time=1&ts=0&ys=0&cs=1&lb=1&sb=0&pb=45&mr=1&regions="
    response = requests.get(url)
    content = response.json()
    proxies["https"] = content["data"][0]["ip"]+":"+str(content["data"][0]["port"])
    return proxies

def get_content(url):
    """发送请求获取数据"""

    #如果报错,停一会,再发,有10次机会,否则返回空字节
    for i in range(5):
        try:
            # 获取图片字节,可能被拦截,加上代理ip
            return requests.get(url, headers=headers, proxies=get_proxies()).content
        except:
            print(url, "失败,尝试第{}次".format(i + 1))
            time.sleep(random.random()*5)

    return b""

def get_data():

    #读数据
    with open("baidu.html", "r", encoding="utf-8") as file:
        html = file.read()
    #通过正则获取img url
    img_list1 = re.findall(r'data-objurl="(.*?)"', html)
    img_list2 = re.findall(r'data-imgurl="(.*?)"', html)
    #合并
    img_list1.extend(img_list2)
    #替换部分不需要的字符
    img_list = map(lambda x:x.replace("amp;",""),img_list1)
    #遍历
    for img in img_list:
        print(img)
        content = get_content(url=img)
        #文件的名字
        filename = "./files/baidu/{}".format(img.split("/")[-1])
        #文件写
        with open(filename,"wb") as file:
            file.write(content)

if __name__ == '__main__':
    #get_html()
    get_data()

美好的日子总是短暂的,虽然还想继续与大家畅谈,但是本篇博文到此已经结束了,如果还嫌不够过瘾,不用担心,我们下篇见

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值