【python】爬取页面的图片

爬取"斗图啦"网站的图片

  • 爬虫
    • 什么是爬虫?
    • robots.txt
    • 爬虫用到的相关的库
    • 工作原理
  • 案例实现

爬虫

什么是爬虫?

网络爬虫,又称网络蜘蛛,网络机器人,是按照一定规则,自动请求万维网网站并提取网络数据的程序或脚本

robots.txt

这个文件一般放在网站的跟目录下,这个文本文件规定了,网站哪些网页可以爬取,哪些网页不可以爬取,robots.txt只是一个协议,没有法律约束力
网站根目录下
【python】爬取页面的图片_第1张图片
我们学院的网站就没有robots.txt
【python】爬取页面的图片_第2张图片

爬虫用到的相关的库

  • urllib:提供了一系列用于操作URL的功能
  • requests:请求指定url网站,得到这个网页
  • bs4:解析网页得到DOM树(String类型)
  • Scrapy:数据分析可视化
  • lxml:解析网页得到DOM树(html文档)
  • threading:多线程,提高爬取速度

工作原理

【python】爬取页面的图片_第3张图片

  • url:统一资源定位符
  • 抓取网页:urllib标准库、requests库(不同于request库)、反爬虫、反反爬虫
  • 数据解析技术:正则表达式、lxml、Json模块、JsonPath
  • 存储爬虫数据:csv文件、excel文件、MongoDB、Redis、Sqlit3

案例实现

import threading,requests,urllib,time
from lxml import etree
#资源池---存放每一张img
SOURCE=[]
#存放每一页的img的url
PAGE_URL_LIST=[]
url="https://www.doutula.com/photo/list/?page="
for i in range(1,6):
    x=url+str(i)   #这里需要转化一下i的数据类型 才可以和url拼接起来
    PAGE_URL_LIST.append(x)
print(PAGE_URL_LIST)
#创建线程锁
lockk=threading.Lock()
#爬取到的图片放到资源池
def put():
    while True:
        #判断PAGE_URL_LIST是否为空 为空表示取完了所有页面
        if len(PAGE_URL_LIST)==0:
            break
        else:
            page_url=PAGE_URL_LIST.pop()  #得到网页url列表里的最后一个 并且把PAGE_URL_LIST的最后一个删除
            headers={
                'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.100 Safari/537.36'
            }
            r=requests.get(page_url,headers=headers)
            r.encoding="utf8"
            text=r.text   #得到字符串的网页
            #解析数据
            html=etree.HTML(text)
            #每次循环拿到一个网页所有图片的urls
            IMG_URLS_PER_PAGE=html.xpath('//div[@class="page-content text-center"]//img/@data-original')
            lockk.acquire()
            for img_url in IMG_URLS_PER_PAGE:
                SOURCE.append(img_url)
            lockk.release()
# def DATE_to_STR():
#     tpl="%Y%m%d%H%M%S"   #time只能精确到秒,不能精确到毫秒,微妙
#     loc=time.localtime()
#     l=time.strftime(tpl,loc)
#     return l
def save():
    while True:
        if len(SOURCE)==0:
            continue   #资源池里没有img_url了不一定是 结束了 可能是put把图片放入资源池的速度慢于save
        else:
            lockk.acquire() #加锁 在保存图片的进程运行时 put进程不运行
            img_url=SOURCE.pop()  #从资源池中拿出一张图片的url
            lockk.release() #解锁
            #img_name=DATE_to_STR()+'.jpg'  #修改文件名
            img_name=img_url.split('/')[-1] #修改文件名
            path='./image/'+img_name
            urllib.request.urlretrieve(img_url,filename=path)
def main():
    for i in range(5):
        th1=threading.Thread(target=put)
        th1.start()
    for i in range(4):
        th2=threading.Thread(target=save)
        th2.start()
    th1.join()  #线程同步,该线程未结束,下面的语句不会执行
    th2.join()
main()
            

你可能感兴趣的:(python,python)