结果展示
由于数据量比较大,我结果只截取了一部分。
代码实现
import requests
from requests.exceptions import RequestException
from lxml import etree
import json
import time
def get_url(num):
"""输入num 生成需要爬取的url"""
url_1 = "http://software.cqupt.edu.cn/info/1006/"
url_2 = ".htm"
url = url_1+str(num)+url_2
#print(url)
return url
def get_one_page(url):
"""爬取一页的源代码,并且返回html"""
try:
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)'
+ 'AppleWebKit/537.36 (KHTML, like Gecko)'
+ 'Chrome/73.0.3683.103 Safari/537.36',
}
response = requests.get(url, headers=headers)
if response.status_code == 200:
response.encoding = "utf-8" #声明‘UTF-8’编译方式,否则乱码
print('爬取成功')
return response.text
else:
print('爬取失败')
fall = response.status_code
print(str(fall))
print(url)
#response.encoding = "utf-8"
#print(response.text)
#print('-----------------------------------------------------------------------------------------------------------------------------------------------------------------')
return response.text
except RequestException:
return None
def dell_one_page(html):
#html1 = etree.parse(html,etree.HTMLParser())#
html1 = etree.HTML(html)
#result = etree.tostring(html1) '就是这行代码把html的格式改了,导致那个新的格式没有了xpath方法'
#print(type(html1))
name = html1.xpath('//p/strong/text()')
what = html1.xpath('//p/text()')
#print(name)
#print(what)
info = {
'name' :name,
'info' :what,
}
infom = {}
#print(info)
#return info
if what:
return info
else:
return infom
def write_download(info):
if info:
with open(r'C:\Users\DDH\Desktop\cquptteachers.txt','a',encoding='utf-8') as f:
f.write(json.dumps(info,ensure_ascii=False)+'\n\n')
else:
with open(r'C:\Users\DDH\Desktop\cquptteachers.txt','a',encoding='utf-8') as f:
f.write("URL错误爬取失败尝试爬取下一个节点"+'\n\n')
def main(num):
'''main函数进行html的爬取'''
url = get_url(num) #生成url
html = get_one_page(url) #将生成的url的html爬取下来
info = dell_one_page(html)
write_download(info)
if __name__ == '__main__':
"""生成num"""
for num in range(1961, 2418, 1):
main(str(num))
time.sleep(1)
主网页分析
本次爬取的URL为:http://software.cqupt.edu.cn/list.jsp?urltype=tree.TreeTempUrl&wbtreeid=1006](http://software.cqupt.edu.cn/list.jsp?urltype=tree.TreeTempUrl&wbtreeid=1006) 传送门
首先进如网站发现全校在职教师的简介:
点击第一名教师进入该教师的个人界面:
而此时的URL变更为了: http://software.cqupt.edu.cn/info/1006/2417.htm 传送们
点击第二名教师进入该教师的个人界面:
此时的URL为:http://software.cqupt.edu.cn/info/1006/2415.htm
分析URL的变换:http://software.cqupt.edu.cn/list.jsp?urltype=tree.TreeTempUrl&wbtreeid=1006
http://software.cqupt.edu.cn/info/1006/2417.htm
http://software.cqupt.edu.cn/info/1006/2415.htm
观察URL的变换可知控制教师信息的URL为URL末尾的四位数字第一位与第二位间隔为2
同时找到下一页的URL:
教师界面分析
查看教师界面的网页源代码:
发现教师的所有信息都在div的id="vsb_content的块当中因此我选择的是XPath,根据这些标签分别写出所需要的信息的选择器。
主要代码分析
一
for num in range(1961, 2418, 1):
main(str(num))
time.sleep(1)
def get_url(num):
"""输入num 生成需要爬取的url"""
url_1 = "http://software.cqupt.edu.cn/info/1006/"
url_2 = ".htm"
url = url_1+str(num)+url_2
#print(url)
return url
首先构建了需要爬取的URL(第一次爬去的时候提取了下一页的URL但是后面发现可以直接控制URL最后四位数字来改变需要爬去的界面,而且第一次爬取时发现URL的不是每一位教师之间相差2,因此在构建URL时选择了构建1961到2418之间的所有URL);
二
def get_one_page(url):
"""爬取一页的源代码,并且返回html"""
try:
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)'
+ 'AppleWebKit/537.36 (KHTML, like Gecko)'
+ 'Chrome/73.0.3683.103 Safari/537.36',
}
response = requests.get(url, headers=headers)
if response.status_code == 200:
response.encoding = "utf-8" #声明‘UTF-8’编译方式,否则乱码
print('爬取成功')
return response.text
else:
print('爬取失败')
fall = response.status_code
print(str(fall))
print(url)
#response.encoding = "utf-8"
#print(response.text)
#print('-----------------------------------------------------------------------------------------------------------------------------------------------------------------')
return response.text
except RequestException:
return None
常规操作,构建headers,然后发送请求,得到访问网页的源代码;
三
def dell_one_page(html):
#html1 = etree.parse(html,etree.HTMLParser())#
html1 = etree.HTML(html)
#result = etree.tostring(html1) '就是这行代码把html的格式改了,导致那个新的格式没有了xpath方法'
#print(type(html1))
name = html1.xpath('//p/strong/text()')
what = html1.xpath('//p/text()')
#print(name)
#print(what)
info = {
'name' :name,
'info' :what,
}
infom = {}
#print(info)
#return info
if what:
return info
else:
return infom
def write_download(info):
if info:
with open(r'C:\Users\DDH\Desktop\cquptteachers.txt','a',encoding='utf-8') as f:
f.write(json.dumps(info,ensure_ascii=False)+'\n\n')
else:
with open(r'C:\Users\DDH\Desktop\cquptteachers.txt','a',encoding='utf-8') as f:
f.write("URL错误爬取失败尝试爬取下一个节点"+'\n\n')
用XPath提取数据,并且保留到本地(我是用的TXT保存的,没钱买不起数据库),因为构建的URL当中有一些URL为空,所以我写出了当URL错误时输出"URL错误爬取失败尝试爬取下一个节点;"
后记
- 这个网站的URL变换没有规律,因此选择直接构建在变换区间当中的所有URL,导致一些URL为空,降低了爬虫的爬取效率;
- 在后期的分析当中发现,每一个教师主页的源代码不一致,也就是说第一个教师的名字可能在p标签当中而第二个教师名字信息在其他标签当中,这导致提取数据时没有统一的提取函数,因此我选择为满足大多数教师主页的网页代码写提取函数,而那些不满足的返回一个【】空的字典;
- 这个网站没有防爬机制,适合像我一样的小白练手;
- 我的第一个爬虫和第一篇博客就这样吧,继续加油,学习ing。