Python多线程结合队列下载百度音乐的方法


Posted in Python onJuly 27, 2015

本文实例讲述了Python多线程结合队列下载百度音乐的方法。分享给大家供大家参考。具体如下:

一直想做个下载音乐的脚本,后来决定就拿百度音乐开刀,经过多次分析,终于制作了一个下载百度音乐的脚本,目前只默认下载第一页,童鞋们可以自由拓展。
适用Windows和Linux平台、依赖BeautifulSoup这个库,主要对HTML进行解析

#!/usr/bin/python
# -*- coding: utf-8 -*-
'''
 百度中批量下载某歌手的歌(目前只下载第一页,可以自行拓展)
 @author:admin
 @qq: 1243385033
'''
import threading, urllib2, os,re,sys
from bs4 import BeautifulSoup
from Queue import Queue
'''目标歌手'''
SINGER = u'亚东'
'''保存路径'''
SAVE_FOLDER = 'F:/music/'
# 查询url
search_url = "http://music.baidu.com/search/song?key=%s&s=1"
# 百度音乐播放盒url
song_url = "http://box.zhangmen.baidu.com/x?op=12&count=1&mtype=1&title="
class Downloader(threading.Thread):
  def __init__(self, task):
    threading.Thread.__init__(self)
    self.task = task
  def run(self):
    '''覆盖父类的run方法'''
    while True:
      url = self.task.get()
      self.download(url)
      self.task.task_done()
  def build_path(self, filename):
    join = os.path.join
    parentPath=join(SAVE_FOLDER,SINGER)
    filename = filename + '.mp3'
    myPath = join(parentPath, filename)
    return myPath
  def download(self, url):
    '''下载文件'''
    sub_url = url.items()
    f_name = sub_url[0][0]
    req_url = sub_url[0][1]
    handle = urllib2.urlopen(req_url)
    # 保存路径
    save_path = self.build_path(f_name)
    with open(save_path, "wb") as handler:
      while True:
        chunk = handle.read(1024)
        if not chunk:
          break
        handler.write(chunk)
        msg = u"已经从 %s下载完成" % req_url
      sys.stdout.write(msg)
      sys.stdout.flush()
class HttpRequest:
  def __init__(self):
    self.task = []
    self.reg_decode = re.compile('<decode>.*?CDATA\[(.*?)\]].*?</decode>')
    self.reg_encode = re.compile('<encode>.*?CDATA\[(.*?)\]].*?</encode>')
    self.init()
    self.target_url = search_url % urllib2.quote(self.encode2utf8(SINGER))
  def encode2utf8(self,source):
    if source and isinstance(source,(str,unicode)):
      source=source.encode("utf8")
      return source
    return source
  def mkDir(self, dir_name):
    if not os.path.exists(dir_name):
      os.mkdir(dir_name)
  def init(self):
    self.mkDir(SAVE_FOLDER)
    subPath = os.path.join(SAVE_FOLDER, SINGER)
    self.mkDir(subPath)
  def http_request(self):
    global song_url
    '''发起请求'''
    response=urllib2.urlopen(self.target_url)
    # 获取头信息
    content = response.read()
    response.close()
    # 使用BeautifulSoup
    html = BeautifulSoup(content, from_encoding="utf8")
    # 提取HTML标签
    span_tag = html.find_all('div', {"monkey":"song-list"})[0].find_all('span', class_='song-title')
      # 遍历List
    for a_tag in span_tag:
      song_name = unicode(a_tag.find_all("a")[0].get_text())
      song_url = song_url + urllib2.quote(self.encode2utf8(song_name))
      song_url = song_url + '$$' + urllib2.quote(self.encode2utf8(SINGER)) + '$$$$&url=&listenreelect=0&.r=0.1696378872729838'
      xmlfile = urllib2.urlopen(song_url)
      xml_content = xmlfile.read()
      xmlfile.close()
      url1 = re.findall(self.reg_encode, xml_content)
      url2 = re.findall(self.reg_decode, xml_content)
      if not url1 or not url2:
        continue
      url = url1[0][:url1[0].rindex('/') + 1] + url2[0]
      self.task.append({song_name:url})
    return self.task
def start_download(urls):
  #创建一个队列
  quene=Queue()
  #获取list的大小
  size=len(urls)
  #开启线程
  for _ in xrange(size):
    t=Downloader(quene)
    t.setDaemon(True)
    t.start()
  #入队列
  for url in urls:
    quene.put(url)
  quene.join()
if __name__=='__main__':
  http=HttpRequest()
  urls=http.http_request()
  start_download(urls)

希望本文所述对大家的Python程序设计有所帮助。

Python 相关文章推荐
在Python操作时间和日期之asctime()方法的使用
May 22 Python
python遍历一个目录,输出所有的文件名的实例
Apr 23 Python
python3 遍历删除特定后缀名文件的方法
Apr 23 Python
Python读取Pickle文件信息并计算与当前时间间隔的方法分析
Jan 30 Python
python程序变成软件的实操方法
Jun 24 Python
用Python实现二叉树、二叉树非递归遍历及绘制的例子
Aug 09 Python
Python搭建代理IP池实现存储IP的方法
Oct 27 Python
python基于event实现线程间通信控制
Jan 13 Python
python实现简单飞行棋
Feb 06 Python
解决pyinstaller 打包exe文件太大,用pipenv 缩小exe的问题
Jul 13 Python
python munch库的使用解析
May 25 Python
如何理解python接口自动化之logging日志模块
Jun 15 Python
在Django框架中设置语言偏好的教程
Jul 27 #Python
在Python的Django框架中创建语言文件
Jul 27 #Python
在Django的模型和公用函数中使用惰性翻译对象
Jul 27 #Python
使用Django的模版来配合字符串翻译工作
Jul 27 #Python
Django中的“惰性翻译”方法的相关使用
Jul 27 #Python
在Python中的Django框架中进行字符串翻译
Jul 27 #Python
Python中特殊函数集锦
Jul 27 #Python
You might like
正义联盟的终局之战《天启星战争》将成为DC动画宇宙的最后一部
2020/04/09 欧美动漫
php处理静态页面:页面设置缓存时间实例
2017/06/22 PHP
Js(JavaScript)中,弹出是或否的选择框示例(confirm用法的实例分析)
2013/07/09 Javascript
IE、FF浏览器下修改标签透明度
2014/01/28 Javascript
在父页面得到zTree已选中的节点的方法
2015/02/12 Javascript
EasyUI实现二级页面的内容勾选的方法
2015/03/01 Javascript
a标签跳转到指定div,jquery添加和移除class属性的实现方法
2016/10/10 Javascript
JavaScript字符集编码与解码详谈
2017/02/02 Javascript
微信小程序 图片宽度自适应的实现
2017/04/06 Javascript
关于axios如何全局注册浅析
2018/01/14 Javascript
bootstrap里bootstrap动态加载下拉框的实例讲解
2018/08/10 Javascript
jQuery实现鼠标移到某个对象时弹出显示层功能
2018/08/23 jQuery
ES6小技巧之代替lodash
2019/06/07 Javascript
Jquery属性的获取/设置及样式添加/删除操作技巧分析
2019/12/23 jQuery
Javascript中Math.max和Math.max.apply的区别和用法详解
2020/08/24 Javascript
pycharm 使用心得(四)显示行号
2014/06/05 Python
Python实现的下载8000首儿歌的代码分享
2014/11/21 Python
JSON Web Tokens的实现原理
2017/04/02 Python
python爬虫 execjs安装配置及使用
2019/07/30 Python
python实现梯度法 python最速下降法
2020/03/24 Python
基于plt.title无法显示中文的快速解决
2020/05/16 Python
Python 代码调试技巧示例代码
2020/08/11 Python
记录一下scrapy中settings的一些配置小结
2020/09/28 Python
详解python百行有效代码实现汉诺塔小游戏(简约版)
2020/10/30 Python
css3实现元素环绕中心点布局的方法示例
2019/01/15 HTML / CSS
科颜氏英国官网:Kiehl’s英国
2019/11/20 全球购物
瑞典最大的儿童用品网上商店:pinkorblue.se
2021/03/09 全球购物
网络安全类面试题
2015/08/01 面试题
《一个中国孩子的呼声》教学反思
2014/02/12 职场文书
个人剖析材料及整改措施
2014/10/07 职场文书
2015年秋季运动会前导词
2015/07/20 职场文书
新西兰:最新留学学习计划书写作指南
2019/07/15 职场文书
MySQL命令行操作时的编码问题详解
2021/04/14 MySQL
Oracle更换为MySQL遇到的问题及解决
2021/05/21 Oracle
python机器学习Github已达8.9Kstars模型解释器LIME
2021/11/23 Python
CSS SandBox应用场景及常见问题
2022/06/25 HTML / CSS