本文选自《精通Python》爬虫第六章,源码爬取过程中有部分问题,因此修改后分享给大家。
注:阅读此文需要掌握Python爬虫的基础知识。推荐此书作为Python爬虫入门书籍,这本书条例很清晰,代码全面,里面讲解的很详细,非常适合新手入门。
import re
import urllib.request
import time
import urllib.error
#模拟成浏览器
headers=('User-Agent','Mozilla/5.0 (Windows NT 6.3; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/49.0.2623.221 Safari/537.36 SE 2.X MetaSr 1.0')
opener=urllib.request.build_opener()
opener.addheaders=[headers]
#opener安装为全局
urllib.request.install_opener(opener)
#设置一个列表listurl存储文章网址列表
listurl=[]
#自定义函数,功能为使用代理服务器
def use_proxy(proxy_addr,url):
#创建异常处理机制
try:
import urllib.request
proxy=urllib.request.ProxyHandler({'http':proxy_addr})
opener=urllib.request.build_opener(proxy,urllib.request.HTTPHandler)
urllib.request.install_opener(opener)
data=urllib.request.urlopen(url).read().decode('utf-8')
print("data1:",data)
return data
except urllib.error.URLError as e:
if hasattr(e,'code'):
print(e.code)
if hasattr(e,'reason'):
print(e.reason)
#若为URLError异常,延迟10秒执行
time.sleep(10)
except Exception as e:
print("exception:"+str(e))
#若为Exception异常,延迟1秒执行
time.sleep(1)
#获取所有文章的链接
def getlisturl(key,pagestart,pageend,proxy=False):
try:
page=pagestart
#编码关键词key
keycode=urllib.request.quote(key)
#编码“&page”
#pagecode=urllib.request.quote("&page")
#print(pagecode)
#循环爬取各页的文章链接
for page in range(pagestart,pageend+1):
#分别构建各页的url链接,每次循环构建一次
url="http://weixin.sogou.com/weixin?type=2&query="+keycode+"&page="+str(page)
print(url)
#用代理服务器解决IP被封杀问题
if proxy==False:
data1=urllib.request.urlopen(url).read().decode('utf-8')
else:
data1=use_proxy(proxy,url)
print(proxy)
#获取文章链接的正则表达式
listurlpat='<div class="txt-box">.*?(http://.*?)"'
#获取每页的文章链接并添加到列表listurl
listurl.append(re.compile(listurlpat,re.S).findall(data1))
print(listurl)
print("共收到"+str(len(listurl))+"页")#便于调试
return listurl
except urllib.error.URLError as e:
if hasattr(e,'code'):
print(e.code)
if hasattr(e,'reason'):
print(e.reason)
#若为URLError异常,延迟10秒执行
time.sleep(10)
except Exception as e:
print("exception:"+str(e))
#若为Exception异常,延迟1秒执行
time.sleep(1)
#通过文章链接获取对应内容
def getcontent(listurl,proxy=False):
i=0
#设置本地文件中的开始html编码
html1='''
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>微信文章页面</title>
</head>
<body>'''
fh=open("D:/pachong/weixin.html",'wb')
fh.write(html1.encode('utf-8'))
fh.close()
#再次以追加的方式打开文件,以写入对应文章内容
fh=open("D:/pachong/weixin.html",'ab')
#此时listurl为二维列表
for i in range(0,len(listurl)):
for j in range(0,len(listurl[i])):
try:
url=listurl[i][j]
url=url.replace("amp;","")
#使用代理爬取对应的网址的内容
if proxy==False:
data=urllib.request.urlopen(url).read().decode('utf-8')
else:
data=use_proxy(proxy,url)
#文章标题正则表达式
titlepat="<title>(.*?)</title>"
#文章内容正则表达式
contentpat='id="js_content">(.*?)id="js_sg_bar"'
title=re.compile(titlepat,re.S).findall(data)
content=re.compile(contentpat,re.S).findall(data)
#初始化标题与内容
thistitle="此次没有获取到"
thiscontent="此次没有获取到"
if(title!=[]):
thistitle=title[0]
if(content!=[]):
thiscontent=content[0]
#将标题与内容汇总后赋值给dataall
dataall="<p>标题为:"+thistitle+"</p><p>内容为:"+thiscontent+"</p><br>"
fh.write(dataall.encode('utf-8'))
print("第"+str(i)+"个网页第"+str(j)+"次处理")#便于调试
except urllib.error.URLError as e:
if hasattr(e,'code'):
print(e.code)
if hasattr(e,'reason'):
print(e.reason)
#若为URLError异常,延迟10秒执行
time.sleep(10)
except Exception as e:
print("exception:"+str(e))
#若为Exception异常,延迟1秒执行
time.sleep(1)
fh.close()
#设置并写入本地文件的html后面的代码
html2='''</body>
</html>
'''
fh=open("D:/weixin.html",'ab')
fh.write(html2.encode('utf-8'))
fh.close()
#设置关键词
key="物联网"
proxy='59.78.8.142:80' #使用代理服务器出问题,因此没有使用
proxy2=""
pagestart=1
pageend=2
listurl=getlisturl(key,pagestart,pageend,proxy=False)
print(listurl)
getcontent(listurl,proxy=False)
致谢
《精通Python网络爬虫》(韦玮著)---机械工业出版社