Python学习 Day55 多线程下载壁纸 04
多线程下载王者荣耀高清壁纸
网址:https://pvp.qq.com/web201605/wallpaper.shtml
一、分析数据URL
1.判读数据是在服务器端继承好再发回浏览器端显示的还是通过Ajax请求发送过来的
- 方式一:点击下一页,观察地址栏是否发生变化,若无变化则是Ajax请求
- 方式二:
2.寻找真实数据源
复制URL到网页中
得到的数据
将其复制到JSON在线解析器
打开图片地址到网页中搜索没有数据
用pycharm代码对图片网址进行解析
#解析URL
from urllib import parse
result = parse.unquote('http%3A%2F%2Fshp.qpic.cn%2Fishow%2F2735040920%2F1617970306_84828260_11438_sProdImgNo_7.jpg%2F200')
print(result)
得到一个可点击的链接
http://shp.qpic.cn/ishow/2735040920/1617970306_84828260_11438_sProdImgNo_7.jpg/200Process finished with exit code 0
点击链接得到壁纸(尺寸最小)
获取尺寸最大的壁纸
分析壁纸URL的规律
至此URL分析完成
- 高清壁纸的URL:https://pvp.qq.com/web201605/wallpaper.shtml
- 含有数据的URL:https://apps.game.qq.com/cgi-bin/ams/module/ishow/V1.0/query/workList_inc.cgi?activityId=2735&sVerifyCode=ABCD&sDataType=JSON&iListNum=20&totalpage=0&page=0&iOrder=0&iSortNumClose=1&jsoncallback=jQuery17109456837125874185_1621073150672&iAMSActivityId=51991&everyRead=true&iTypeId=2&iFlowId=267733&iActId=2735&iModuleId=2735&=1621073150953
- 页码范围:一共25页,为0到24
二、爬取第一页数据
- 添加请求头参数headers和referer应对反爬
- urllib下的parse解析URL与解码中文编码
import requests
headers = {'user-agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.212 Safari/537.36',
'referer':'https://pvp.qq.com/'
}
def send_requests():url = 'https://apps.game.qq.com/cgi-bin/ams/module/ishow/V1.0/query/workList_inc.cgi?activityId=2735&sVerifyCode=ABCD&sDataType=JSON&iListNum=20&totalpage=0&page=0&iOrder=0&iSortNumClose=1&jsoncallback=jQuery171006071737506646002_1621078799273&iAMSActivityId=51991&_everyRead=true&iTypeId=2&iFlowId=267733&iActId=2735&iModuleId=2735&_=1621078799790'resp = requests.get(url,headers=headers)print(resp.text)def start():send_requests()if __name__ == '__main__':start()
结果是不符合JSON数据格式的对象
去掉数据URL中的jsoncallback参数
得到符合JSON格式规范的数据
解析json数据
import requests
from urllib import parse
headers = {'user-agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.212 Safari/537.36',
'referer':'https://pvp.qq.com/'
}def exact_utl(data):'''提前每个字典当中的八张壁纸'''image_url_lst = [] #存储链接的列表for i in range(1,9): #注意索引是从1开始的# 解析获取到的URL,并将地址尾数200替换成0image_url = parse.unquote(data['sProdImgNo_{}'.format(i)]).replace('200','0')image_url_lst.append(image_url)return image_url_lst #返回图片的URLdef send_requests():url = 'https://apps.game.qq.com/cgi-bin/ams/module/ishow/V1.0/query/workList_inc.cgi?activityId=2735&sVerifyCode=ABCD&sDataType=JSON&iListNum=20&totalpage=0&page=0&iOrder=0&iSortNumClose=1&_everyRead=true&iTypeId=2&iFlowId=267733&iActId=2735&iModuleId=2735&_=1621078799790'resp = requests.get(url,headers=headers)#print(resp.text)return resp.json()def parse_json(json_data):'''解析json数据'''d = {} #用于存放壁纸名和壁纸URL的字典data_list = json_data['List'] #获得一个列表for data in data_list:image_url_lst = exact_utl(data)sProdName = parse.unquote(data['sProdName']) #获取壁纸名称并解析d[sProdName] = image_url_lstfor item in d:print(item,d[item])def start():json_data = send_requests() #返回数据是一个json对象parse_json(json_data)if __name__ == '__main__':start()
三、存储壁纸
- 路径的拼接
- os.mkdir()创建文件夹
- requests.urlretrieve(url,path)从URL处下载并存储到path中
import requests
from urllib import parse
import os
from urllib import request
headers = {'user-agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.212 Safari/537.36',
'referer':'https://pvp.qq.com/'
}def exact_utl(data):'''提取每个字典当中的八张壁纸'''image_url_lst = [] #存储链接的列表for i in range(1,9): #注意索引是从1开始的# 解析获取到的URL,并将地址尾数200替换成0image_url = parse.unquote(data['sProdImgNo_{}'.format(i)]).replace('200','0')image_url_lst.append(image_url)return image_url_lst #返回图片的URLdef send_requests():url = 'https://apps.game.qq.com/cgi-bin/ams/module/ishow/V1.0/query/workList_inc.cgi?activityId=2735&sVerifyCode=ABCD&sDataType=JSON&iListNum=20&totalpage=0&page=0&iOrder=0&iSortNumClose=1&_everyRead=true&iTypeId=2&iFlowId=267733&iActId=2735&iModuleId=2735&_=1621078799790'resp = requests.get(url,headers=headers)#print(resp.text)return resp.json()def parse_json(json_data):'''解析json数据'''d = {} #用于存放壁纸名和壁纸URL的字典data_list = json_data['List'] #获得一个列表for data in data_list:image_url_lst = exact_utl(data)sProdName = parse.unquote(data['sProdName']) #获取壁纸名称并解析d[sProdName] = image_url_lst'''for item in d:print(item,d[item])'''save_jpg(d)def save_jpg(d):'''保存图片'''for key in d:# 拼接路径 image/李白-凤求凰'''dirpath = os.path.join('image',key.strip(' ') 去掉空格os.mkdir(dirpath)'''dirpath = 'image/'+keyif not os.path.exists(dirpath):# 创建文件夹os.mkdir(dirpath)# 下载图片并进行保存for index,image_url in enumerate(d[key]):#request.urlretrieve()方法:打开图片的URL并下载到文件中request.urlretrieve(image_url,os.path.join(dirpath,'{}.jpg').format(index+1))print('{}下载完毕'.format(d[key][index]))def start():json_data = send_requests() #返回数据是一个json对象parse_json(json_data)if __name__ == '__main__':start()
第一页壁纸下载完毕
四、多线程下载壁纸
生产者线程:生产图片路径
- page_queue
- page_queue.get()
- image_url_queue
- image_url_queue.put()
消费者线程:下载图片并进行存储
- image_url_queue
- image_url_queue.get()
获取每一页的URL,修改原URL中的page=0为page={i}
import requests
from urllib import parse
from queue import Queue
import threading
import os
from urllib import requestheaders = {'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.212 Safari/537.36','referer': 'https://pvp.qq.com/'
}def exact_utl(data):'''提取每个字典当中的八张壁纸'''image_url_lst = [] # 存储链接的列表for i in range(1, 9): # 注意索引是从1开始的# 解析获取到的URL,并将地址尾数200替换成0image_url = parse.unquote(data['sProdImgNo_{}'.format(i)]).replace('200', '0')image_url_lst.append(image_url)return image_url_lst # 返回图片的URL# 生产者线程
class Producer(threading.Thread):def __init__(self, page_queue, image_url_queue):super().__init__()self.page_queue = page_queueself.image_url_queue = image_url_queuedef run(self):# 如果队列不为空while not self.page_queue.empty():# 则从队列当中取出URLpage_url = self.page_queue.get()# 取出URL后发送请求resp = requests.get(page_url, headers=headers)# 将返回的resp对象转换成json数据格式json_data = resp.json()# 数据的提取d = {} # 用于存放壁纸名和壁纸URL的字典data_list = json_data['List'] # 获得一个列表for data in data_list:image_url_lst = exact_utl(data) # 图片URL的列表sProdName = parse.unquote(data['sProdName']) # 获取壁纸名称并解析d[sProdName] = image_url_lst# 创建文件夹并存放数据for key in d:'''dirpath = os.path.join('image',key.strip(' ').replace('·','').replace('1:1','') 去掉空格,“·”,“1:1”等中文字符os.mkdir(dirpath)'''dirpath = 'image/' + keyif not os.path.exists(dirpath):# 创建文件夹os.mkdir(dirpath)# 下载图片并进行保存for index, image_url in enumerate(d[key]):# 生产图片的URLself.image_url_queue.put({'image_path': os.path.join(dirpath, f'{index + 1}.jpg'), 'image_url': image_url})# 消费者线程
class Customer(threading.Thread):def __init__(self, image_url_queue):super().__init__()self.image_url_queue = image_url_queuedef run(self):while True:try:# 取出生产者线程生产的图片URL# timeout参数,若程序超过20s还未响应则停止image_obj = self.image_url_queue.get(timeout=20)request.urlretrieve(image_obj['image_url'], image_obj['image_path'])print(f'{image_obj["image_path"]}下载完成')except:break# 启动线程
def start():# 存储每一页URL的队列,共25页page_queue = Queue(25)# 存储图片的路径image_url_queue = Queue(1000)for i in range(0, 1):page_url = f'https://apps.game.qq.com/cgi-bin/ams/module/ishow/V1.0/query/workList_inc.cgi?activityId=2735&sVerifyCode=ABCD&sDataType=JSON&iListNum=20&totalpage=0&page={i}&iOrder=0&iSortNumClose=1&_everyRead=true&iTypeId=2&iFlowId=267733&iActId=2735&iModuleId=2735&_=1621078799790'# print(page_url)page_queue.put(page_url)# 创建生产者线程对象for i in range(5):t = Producer(page_queue, image_url_queue)t.start()# 创建消费者线程对象for i in range(10):t = Customer(image_url_queue)t.start()if __name__ == '__main__':start()
Python学习 Day55 多线程下载壁纸 04相关推荐
- Python爬虫(二)——多线程下载壁纸图片(星月设计网)
文章目录 Python爬虫--多线程下载图片(星月设计网) 目的: redis存储结构: 使用到的python库: 1. 导入相关库 2. 连接redis 3.爬虫主要类及函数 4.爬取结果: Pyt ...
- 【python学习】多线程下载图片实战
python多线程下载图片(setu) 前言 python的学习其实早在两三个星期前就开始了,奈何我是个急性子,所以学的很浮躁,甚至连md笔记都没写.但是想了想,我学python的目的反正也仅仅是为了 ...
- python多线程下载ts_基于Python的ERA-5多线程下载(1)
目录 基于Python的ERA-5多线程下载分为两部分,<基于Python的ERA-5多线程下载 (1)>,直接再本地使用,即写代码的人使用:<基于Python的ERA-5多线程下载 ...
- python学习笔记——多线程编程
python学习笔记--多线程编程 基础不必多讲,还是直接进入python. Python代码代码的执行由python虚拟机(也叫解释器主循环)来控制.Python在设计之初就考虑到要在主循环中,同时 ...
- 爬虫:程序_进程_线程_多线程(案例多线程下载壁纸)
目录 前言 一.什么是程序_进程_线程? 二.实现多线程的方法 继承方式实现多线程 为什么要是用类的方式创建线程: 线程的一些常用方法: 三.多线程访问全局变量的安全性问题: 什么是线程安全: 四.解 ...
- [python学习] 模仿浏览器下载CSDN源文并实现PDF格式备份
最近突然想给自己的博客备份下,看了两个软件:一个是CSDN博客导出软件,好像现在不能使用了:一个是豆约翰博客备份专家,感觉都太慢,而且不灵活,想单独下一篇文章就比较费时.而且我的毕业论文是基于Pyth ...
- 【python实战】多线程下载文件
点赞再看,养成好习惯 哈喽,大家好,我是一条. 相信大家都遇到过下载文件过慢的时候,今天教大家多线程下载,快到飞起. 1.实现原理 根据url后利用request库获得数据,保存到文件. 将文件分成若 ...
- python壁纸程序代码_python批量下载壁纸的实现代码
复制代码 代码如下: #! /usr/bin/env python ##python2.7-批量下载壁纸 ##壁纸来自桌酷网站,所有权归属其网站 ##本代码仅做为交流学习使用,请勿用于商业用途,否则后 ...
- 【python爬虫】实现多线程下载器
写在前面 为什么要多线程?单个线程不能下载吗?多线程能占满网络实现宽带的满速下载而单线程不能. 举个栗子:你的宽带是100Mb/s,理论上最大下载速度是100/8=12.5MB/s.你要下载一个843 ...
- 零基础学Python学习笔记
Python学习笔记 代码下载地址 链接:https://pan.baidu.com/s/1yGnpfq4ZHeKpt4V0J_PTSg 提取码:hmzs 1. Python 基础语法 1.1 基本数 ...
最新文章
- android 自定义radiobutton 样式,RadioButton自定义点击时的背景颜色
- 中国-中东欧国家特色农产品 云上国际农民丰收节贸易会
- python 如何将字符串列表合并后转换成字符串? ''.join(List(str))函数
- windows下使用curl以及常用curl命令
- AndroidStudio部署项目时出现错误:Instant Run requires 'Tools | Android | Enable ADB integration' to be enabled
- 2017二级c语言成绩,2017全国计机等级考试二级C语言知识点超全整(打印版).docx
- LeetCode 1656. 设计有序流(数组)
- 执行后可以查看python的版本的是_windows肿么查看python opencv 版本
- 简说 Python 生态系统的 14 年演变
- covariance matrix r语言_R语言 第2章 数据对象与数据读写(3)
- SSH中 三大框架的各自的作用及好处
- 爱的历史摘录(西蒙·梅)
- Excel如何制作斜线表头
- 共享计算机如何重新登录密码,电脑共享后怎么登陆密码怎样设置
- linux加法计算器程序,Linux下实现一个计算器程序
- swagger出现no response from server错误的解决办法
- 2022年食盐市场现状
- 使用层次聚类在结构点云中进行平面的快速提取
- 艾洛积分系统(Elo Rating System)
- 小程序实现老虎机抽奖动画