python queue查询空_【Python】多线程爬虫案例
爬取博客园文章列表
爬取博客园文章列表,假设页面的URL是https://www.cnblogs.com/loaderman
要求:使用requests获取页面信息,用XPath / re 做数据提取 获取每个博客里的标题,描述,链接地址,日期等保存到 json 文件内
示例:
# -*- coding:utf-8 -*-
import urllib2import jsonfrom lxml import etree
url = "https://www.cnblogs.com/loaderman/"headers = {"User-Agent": "Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Trident/5.0;"}
request = urllib2.Request(url, headers=headers)
html = urllib2.urlopen(request).read()# 响应返回的是字符串,解析为HTML DOM模式 text = etree.HTML(html)
text = etree.HTML(html)# 返回所有结点位置,contains()模糊查询方法,第一个参数是要匹配的标签,第二个参数是标签名部分内容node_list = text.xpath('//div[contains(@class, "post")]')print (node_list)items = {}for each in node_list: print (each) title = each.xpath(".//h2/a[@class='postTitle2']/text()")[0] detailUrl = each.xpath(".//a[@class='postTitle2']/@href")[0] content = each.xpath(".//div[@class='c_b_p_desc']/text()")[0] date = each.xpath(".//p[@class='postfoot']/text()")[0]
items = { "title": title, "image": detailUrl, "content": content, "date": date,
}
with open("loaderman.json", "a") as f: f.write(json.dumps(items, ensure_ascii=False).encode("utf-8") + "\n")
效果:
多线程爬虫案例
Queue是python中的标准库,可以直接import Queue引用;队列是线程间最常用的交换数据的形式
python下多线程的思考
对于资源,加锁是个重要的环节。因为python原生的list,dict等,都是not thread safe的。而Queue,是线程安全的,因此在满足使用条件下,建议使用队列
初始化:class Queue.Queue(maxsize) FIFO 先进先出
包中的常用方法:
Queue.qsize() 返回队列的大小
Queue.empty() 如果队列为空,返回True,反之False
Queue.full() 如果队列满了,返回True,反之False
Queue.full 与 maxsize 大小对应
Queue.get([block[, timeout]])获取队列,timeout等待时间
创建一个“队列”对象
import Queue
myqueue = Queue.Queue(maxsize = 10)
将一个值放入队列中
myqueue.put(10)
将一个值从队列中取出
myqueue.get()
示意图:
# -*- coding:utf-8 -*-
# 使用了线程库import threading# 队列from Queue import Queue# 解析库from lxml import etree# 请求处理import requests# json处理import jsonimport time
class ThreadCrawl(threading.Thread): def __init__(self, threadName, pageQueue, dataQueue): # threading.Thread.__init__(self) # 调用父类初始化方法 super(ThreadCrawl, self).__init__() # 线程名 self.threadName = threadName # 页码队列 self.pageQueue = pageQueue # 数据队列 self.dataQueue = dataQueue # 请求报头 self.headers = {"User-Agent": "Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Trident/5.0;"}
def run(self): print "启动 " + self.threadName while not CRAWL_EXIT: try: # 取出一个数字,先进先出 # 可选参数block,默认值为True # 1. 如果对列为空,block为True的话,不会结束,会进入阻塞状态,直到队列有新的数据 # 2. 如果队列为空,block为False的话,就弹出一个Queue.empty()异常, page = self.pageQueue.get(False) url = "https://www.cnblogs.com/loaderman/default.html?page=" + str(page) # print url content = requests.get(url, headers=self.headers).text time.sleep(1) self.dataQueue.put(content) # print len(content) except: pass print "结束 " + self.threadName
class ThreadParse(threading.Thread): def __init__(self, threadName, dataQueue, filename, lock): super(ThreadParse, self).__init__() # 线程名 self.threadName = threadName # 数据队列 self.dataQueue = dataQueue # 保存解析后数据的文件名 self.filename = filename # 锁 self.lock = lock
def run(self): print "启动" + self.threadName while not PARSE_EXIT: try: html = self.dataQueue.get(False) self.parse(html) except: pass print "退出" + self.threadName
def parse(self, html): # 解析为HTML DOM html = etree.HTML(html)
node_list = html.xpath('//div[contains(@class, "post")]') print (node_list) items = {} for each in node_list: print (each) title = each.xpath(".//h2/a[@class='postTitle2']/text()")[0] detailUrl = each.xpath(".//a[@class='postTitle2']/@href")[0] content = each.xpath(".//div[@class='c_b_p_desc']/text()")[0] date = each.xpath(".//p[@class='postfoot']/text()")[0]
items = { "title": title, "image": detailUrl, "content": content, "date": date,
}
with open("loadermanThread.json", "a") as f: f.write(json.dumps(items, ensure_ascii=False).encode("utf-8") + "\n")
CRAWL_EXIT = FalsePARSE_EXIT = False
def main(): # 页码的队列,表示20个页面 pageQueue = Queue(20) # 放入1~10的数字,先进先出 for i in range(1, 21): pageQueue.put(i)
# 采集结果(每页的HTML源码)的数据队列,参数为空表示不限制 dataQueue = Queue()
filename = open("duanzi.json", "a") # 创建锁 lock = threading.Lock()
# 三个采集线程的名字 crawlList = ["采集线程1号", "采集线程2号", "采集线程3号"] # 存储三个采集线程的列表集合 threadcrawl = [] for threadName in crawlList: thread = ThreadCrawl(threadName, pageQueue, dataQueue) thread.start() threadcrawl.append(thread)
# 三个解析线程的名字 parseList = ["解析线程1号", "解析线程2号", "解析线程3号"] # 存储三个解析线程 threadparse = [] for threadName in parseList: thread = ThreadParse(threadName, dataQueue, filename, lock) thread.start() threadparse.append(thread)
# 等待pageQueue队列为空,也就是等待之前的操作执行完毕 while not pageQueue.empty(): pass
# 如果pageQueue为空,采集线程退出循环 global CRAWL_EXIT CRAWL_EXIT = True
print "pageQueue为空"
for thread in threadcrawl: thread.join() print "1"
while not dataQueue.empty(): pass
global PARSE_EXIT PARSE_EXIT = True
for thread in threadparse: thread.join() print "2"
with lock: # 关闭文件 filename.close() print "谢谢使用!"
if __name__ == "__main__": main()
效果:
完
码上加油站
一起来加油
长按扫码关注
记得点个赞和在看哦!
python queue查询空_【Python】多线程爬虫案例相关推荐
- python实现一个很简单的多线程爬虫
需求 无聊用python写一个爬虫爬取某个视频网站的内容,获取名称地址时长和更新时间保存到数据库头,以前没用过也没学多线程所以接直接顺着来,按照python的简洁性几行代码就搞定,一刷下来没问题,保存 ...
- python多线程爬虫案例之爬取麦田
import threading import requests from time import sleep from bs4 import BeautifulSoup import csv fro ...
- python课表查询系统_使用python抓取广西科技大学教务系统课程表
因学校教务系统课程表查询功能累赘,服务器经常挂,同时也不适合手机端查询,所以用python开发爬虫抓取所有课程表,放到我的服务器上面. 本文仅供学习. 特性 中途退出程序再次运行不会抓取到重复课程表 ...
- python多进程编程实例_[python] Python多进程编程技术实例分析
这篇文章主要介绍了Python多进程编程技术,包括了线程.队列.同步等概念及相关的技巧总结,需要的朋友可以参考下 本文以实例形式分析了Python多进程编程技术,有助于进一步Python程序设计技巧. ...
- python查看excel编码格式_[Python]实现处理读写xlsx xls excel文件格式(含中文处理方法)...
最近有个需求要处理excel 格式的数据,数据量比较大.用传统的语言似乎不太好处理,于是改用python实现,这里记录一下实现过程. 首先,科普一下xlsx xls的excel文件区别是什么. xls ...
- python朋友圈刷屏_“Python太火了!请救救Java!”9万程序员刷屏朋友圈 !
没想到有生之年,笔者能观察到"霸主陨落"的过程,继PLPY4月榜单官宣,Python躺赢,再度"夺"冠,实力甩下Java和C后,近期,Stack Overflo ...
- python 打包 小文件_[Python][小知识][NO.5] 使用 Pyinstaller 打包成.exe文件
1.安装 pyinstaller 插件 cmd命令:pip install PyInstaller PS . o.o 不知道 easy_install 的百度吧. 2.pyinstaller 简介 他 ...
- python shell如何打开_“python shell怎么打开“python shell启动教程
python shell怎么打开 1.简介:如何在python中运行shell(bash命令) 2.工具/原料:python库:os.py 3.方法:import os command = 'date ...
- python输出文本居中_#python PIL ImageDraw text 文本居中#
python pip pil有什么东西 你所问的问题实是属1.先参考[教程]Python中的内置的和方的模块搞懂PIL是属于第三方Python模块2.再参考:[待完善][总结]Python安装第三方的 ...
最新文章
- Web项目使用nginx实现代理端口访问,看这篇就够了
- 大数据学习笔记二:Ubuntu/Debian 下安装大数据框架Hadoop
- 2014家电盘点:求变与创新
- 提高显微镜分辨率方法_超分辨显微镜研究获进展
- Michael A. Cusumano
- what to do to make a phone call at dorm?
- php实现商品购物车添加功能,PHP实现添加购物车功能
- linux耳机检测,Audio Jack 的耳机检测和按键检测
- html%3ca%3e标签,How do I encode “” in a URL in an HTML attribute value?
- 【java笔记】File类(3):FileFilter文件过滤器原理和使用
- Tiny4412 小试牛刀
- 2020年西南交通大学数据仓库与数据挖掘期末考试题
- BZOJ2565最长双回文串——manacher
- 程序员刷简历领导看见很寒心,网友:找工作也要经过你同意?
- [敏捷开发培训] 燃尽图(Burndown Chart)
- 将https安全证书导入jdk中
- Spark:图(Graph)
- visibility的用法
- 19.3 Table 1-2.S3C2440A 289-Pin FBGA Pin Assignments (Sheet 4 of 9) (Continued)
- 某度网盘不限速下载,这里有个新方法~
热门文章
- MySQL:日期函数、时间函数总结
- springboot 使用 minio
- python代码html显示数据_通过AJAX success方法以html格式显示数据
- mysql事务和非事物_mysql事务型与非事务型表1.8.5.3. 事务和原子操作
- java if两个条件_java(3) if结构
- 城市运行一网统管_全国率先!“一屏观天下、一网管全城”,临港城市运行“一网统管”平台启动建设...
- 排序算法 —— 堆排序
- 哈希表的大小为何最好是素数
- rabbitmq+topic+java_译:5.RabbitMQ Java Client 之 Topics (主题)
- PHP定时抽奖怎么实现的,PHP 实现抽奖逻辑