python支持多线程的爬虫实例


Posted in Python onDecember 21, 2019

python是支持多线程的, 主要是通过thread和threading这两个模块来实现的,本文主要给大家分享python实现多线程网页爬虫

一般来说,使用线程有两种模式, 一种是创建线程要执行的函数, 把这个函数传递进Thread对象里,让它来执行. 另一种是直接从Thread继承,创建一个新的class,把线程执行的代码放到这个新的class里。

实现多线程网页爬虫,采用了多线程和锁机制,实现了广度优先算法的网页爬虫。

先给大家简单介绍下我的实现思路:

对于一个网络爬虫,如果要按广度遍历的方式下载,它是这样的:

1.从给定的入口网址把第一个网页下载下来

2.从第一个网页中提取出所有新的网页地址,放入下载列表中

3.按下载列表中的地址,下载所有新的网页

4.从所有新的网页中找出没有下载过的网页地址,更新下载列表

5.重复3、4两步,直到更新后的下载列表为空表时停止

python代码如下:

#!/usr/bin/env python
#coding=utf-8
import threading
import urllib
import re
import time
g_mutex=threading.Condition()
g_pages=[] #从中解析所有url链接
g_queueURL=[] #等待爬取的url链接列表
g_existURL=[] #已经爬取过的url链接列表
g_failedURL=[] #下载失败的url链接列表
g_totalcount=0 #下载过的页面数
class Crawler:
 def __init__(self,crawlername,url,threadnum):
  self.crawlername=crawlername
  self.url=url
  self.threadnum=threadnum
  self.threadpool=[]
  self.logfile=file("log.txt",'w')
 def craw(self):
  global g_queueURL
  g_queueURL.append(url) 
  depth=0
  print self.crawlername+" 启动..."
  while(len(g_queueURL)!=0):
   depth+=1
   print 'Searching depth ',depth,'...\n\n'
   self.logfile.write("URL:"+g_queueURL[0]+"........")
   self.downloadAll()
   self.updateQueueURL()
   content='\n>>>Depth '+str(depth)+':\n'
   self.logfile.write(content)
   i=0
   while i<len(g_queueURL):
    content=str(g_totalcount+i)+'->'+g_queueURL[i]+'\n'
    self.logfile.write(content)
    i+=1
 def downloadAll(self):
  global g_queueURL
  global g_totalcount
  i=0
  while i<len(g_queueURL):
   j=0
   while j<self.threadnum and i+j < len(g_queueURL):
    g_totalcount+=1
    threadresult=self.download(g_queueURL[i+j],str(g_totalcount)+'.html',j)
    if threadresult!=None:
     print 'Thread started:',i+j,'--File number =',g_totalcount
    j+=1
   i+=j
   for thread in self.threadpool:
    thread.join(30)
   threadpool=[]
  g_queueURL=[]
 def download(self,url,filename,tid):
  crawthread=CrawlerThread(url,filename,tid)
  self.threadpool.append(crawthread)
  crawthread.start()
 def updateQueueURL(self):
  global g_queueURL
  global g_existURL
  newUrlList=[]
  for content in g_pages:
   newUrlList+=self.getUrl(content)
  g_queueURL=list(set(newUrlList)-set(g_existURL)) 
 def getUrl(self,content):
  reg=r'"(http://.+?)"'
  regob=re.compile(reg,re.DOTALL)
  urllist=regob.findall(content)
  return urllist
class CrawlerThread(threading.Thread):
 def __init__(self,url,filename,tid):
  threading.Thread.__init__(self)
  self.url=url
  self.filename=filename
  self.tid=tid
 def run(self):
  global g_mutex
  global g_failedURL
  global g_queueURL
  try:
   page=urllib.urlopen(self.url)
   html=page.read()
   fout=file(self.filename,'w')
   fout.write(html)
   fout.close()
  except Exception,e:
   g_mutex.acquire()
   g_existURL.append(self.url)
   g_failedURL.append(self.url)
   g_mutex.release()
   print 'Failed downloading and saving',self.url
   print e
   return None
  g_mutex.acquire()
  g_pages.append(html)
  g_existURL.append(self.url)
  g_mutex.release()
if __name__=="__main__":
 url=raw_input("请输入url入口:\n")
 threadnum=int(raw_input("设置线程数:"))
 crawlername="小小爬虫"
 crawler=Crawler(crawlername,url,threadnum)
 crawler.craw()

以上这篇python支持多线程的爬虫实例就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
python numpy元素的区间查找方法
Nov 14 Python
使用Template格式化Python字符串的方法
Jan 22 Python
Python 数据库操作 SQLAlchemy的示例代码
Feb 18 Python
python lxml中etree的简单应用
May 10 Python
Python中asyncio模块的深入讲解
Jun 10 Python
python list多级排序知识点总结
Oct 23 Python
pandas实现DataFrame显示最大行列,不省略显示实例
Dec 26 Python
Python利用FFT进行简单滤波的实现
Feb 26 Python
Django调用百度AI接口实现人脸注册登录代码实例
Apr 23 Python
Python使用sys.exc_info()方法获取异常信息
Jul 23 Python
python基础之while循环语句的使用
Apr 20 Python
Python机器学习算法之决策树算法的实现与优缺点
May 13 Python
Python 实现try重新执行
Dec 21 #Python
在python shell中运行python文件的实现
Dec 21 #Python
Python 脚本的三种执行方式小结
Dec 21 #Python
python带参数打包exe及调用方式
Dec 21 #Python
python脚本后台执行方式
Dec 21 #Python
Python模块的制作方法实例分析
Dec 21 #Python
基于Python 中函数的 收集参数 机制
Dec 21 #Python
You might like
frename PHP 灵活文件命名函数 frename
2009/09/09 PHP
PHP使用DOMDocument类生成HTML实例(包含常见标签元素)
2014/06/25 PHP
PHP实现服务器状态监控的方法
2014/12/09 PHP
js tab效果的实现代码
2009/12/26 Javascript
Javascript面向对象之四 继承
2011/02/08 Javascript
中国地区三级联动下拉菜单效果分析
2012/11/15 Javascript
Extjs 3.3切换tab隐藏相应工具栏出现空白解决
2013/04/02 Javascript
js实现的map方法示例代码
2014/01/13 Javascript
js数组去重的常用方法总结
2014/01/24 Javascript
使用Jasmine和Karma对AngularJS页面程序进行测试
2016/03/05 Javascript
JS中对象与字符串的互相转换详解
2016/05/20 Javascript
基于Bootstrap的Java开发问题汇总(Spring MVC)
2017/01/15 Javascript
jQuery中extend函数简单用法示例
2017/10/11 jQuery
VUE前端cookie简单操作
2017/10/17 Javascript
使用Vue写一个datepicker的示例
2018/01/27 Javascript
vue2.0模拟锚点的实例
2018/03/14 Javascript
nodejs基础之buffer缓冲区用法分析
2018/12/26 NodeJs
node基于async/await对mysql进行封装
2019/06/20 Javascript
Python使用正则表达式实现文本替换的方法
2017/04/18 Python
python主线程捕获子线程的方法
2018/06/17 Python
python定向爬虫校园论坛帖子信息
2018/07/23 Python
python 同时运行多个程序的实例
2019/01/07 Python
详解DeBug Python神级工具PySnooper
2019/07/03 Python
借助Paramiko通过Python实现linux远程登陆及sftp的操作
2020/03/16 Python
keras自定义回调函数查看训练的loss和accuracy方式
2020/05/23 Python
Python用摘要算法生成token及检验token的示例代码
2020/12/01 Python
英国Office鞋店德国网站:在线购买鞋子、靴子和运动鞋
2018/12/19 全球购物
汽车维修专业毕业生的求职信分享
2013/12/04 职场文书
部队党性分析材料
2014/02/16 职场文书
2014年医院十一国庆节活动方案
2014/09/15 职场文书
社区文明创建工作总结2015
2015/04/21 职场文书
小学数学教学随笔
2015/08/14 职场文书
《游戏公平》教学反思
2016/02/20 职场文书
小学三年级作文之写景
2019/11/05 职场文书
Pyhton模块和包相关知识总结
2021/05/12 Python
52条SQL语句教你性能优化
2021/05/25 MySQL