一、主题式网络爬虫设计方案
1.主题式网络爬虫名称:爬取全网热点榜单数据
2.主题式网络爬虫爬取的内容与数据特征分析:
1)热门榜单;
2)数据有日期、标题、链接地址等
3.主题式网络爬虫设计方案概述:
1)HTML页面分析得到HTML代码结构;
2)程序实现:
a. 定义代码字典;
b. 用requests抓取网页信息;
c. 用BeautifulSoup库解析网页;
d. 用pandas库保存数据为xls;
e. 定义主函数main();
f. 定义功能函数,解耦;
二、主题页面的结构特征分析
1.主题页面的结构与特征分析(网页地址:https://tophub.today/):
2.Html页面解析
3.节点(标签)查找方法与遍历方法:使用 find_all() 和 find() 方法寻找关键class获取数据
三、网络爬虫程序设计
1.数据爬取与采集
用requests抓取网页信息,设置UA(User-Agent),访问获取网页数据;
部分代码:
import requests
def getHtml(url):
headers = {'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/538.55 (KHTML, like Gecko) Chrome/81.0.3345.132 Safari/538.55'}
resp = requests.get(url, headers=headers)
return resp.text
部分运行截图:
2.对数据进行清洗和处理
用BeautifulSoup库解析网页,find_all()方法寻找需要的数据,然后find()方法通过class标签寻找关键数据;
部分代码:
from bs4 import BeautifulSoup
def get_data(html):
soup = BeautifulSoup(html, 'html.parser')
nodes = soup.find_all('div', class_='cc-cd')
return nodes
def get_node_data(df, nodes):
now = int(time.time())
for node in nodes:
source = node.find('div', class_='cc-cd-lb').text.strip()
messages = node.find('div', class_='cc-cd-cb-l nano-content').find_all('a')
for message in messages:
content = message.find('span', class_='t').text.strip()
if source == '微信':
reg = '「.+?」(.+)'
content = re.findall(reg, content)[0]
if df.empty or df[df.content == content].empty:
data = {
'content': [content],
'url': [message['href']],
'source': [source],
'start_time': [now],
'end_time': [now]
}
item = pandas.DataFrame(data)
df = pandas.concat([df, item], ignore_index=True)
else:
index = df[df.content == content].index[0]
df.at[index, 'end_time'] = now
return df
部分运行截图:
3.数据持久化
用pandas库保存数据为xls;
部分代码:
import pandas
res = pandas.read_excel('tophub.xlsx')
res = get_node_data(res, data)
res.to_excel('tophub.xlsx')
部分运行截图:
4.将以上各部分的代码汇总,完整代码:
import requests
from bs4 import BeautifulSoup
import time
import pandas
import re
def getHtml(url):
headers = {'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/538.55 (KHTML, like Gecko) Chrome/81.0.3345.132 Safari/538.55'}
resp = requests.get(url, headers=headers)
return resp.text
def get_data(html):
soup = BeautifulSoup(html, 'html.parser')
nodes = soup.find_all('div', class_='cc-cd')
return nodes
def get_node_data(df, nodes):
now = int(time.time())
for node in nodes:
source = node.find('div', class_='cc-cd-lb').text.strip()
messages = node.find('div', class_='cc-cd-cb-l nano-content').find_all('a')
for message in messages:
content = message.find('span', class_='t').text.strip()
if source == '微信':
reg = '「.+?」(.+)'
content = re.findall(reg, content)[0]
if df.empty or df[df.content == content].empty:
data = {
'content': [content],
'url': [message['href']],
'source': [source],
'start_time': [now],
'end_time': [now]
}
item = pandas.DataFrame(data)
df = pandas.concat([df, item], ignore_index=True)
else:
index = df[df.content == content].index[0]
df.at[index, 'end_time'] = now
return df
url = 'https://tophub.today'
html = getHtml(url)
data = get_data(html)
res = pandas.read_excel('tophub.xlsx')
res = get_node_data(res, data)
res.to_excel('tophub.xlsx')
四、结论
本次程序设计任务补考,我选择的课题是爬取全网热门榜单聚合数据,并不是每个网站的榜单数据,平时也经常使用这个网站关注全国的热点资讯。对于这个网站的爬取相对简单也比较熟悉,首先它是一个静态网页,其次节点也相当好找,通过class标签就可以轻松找到,而且爬虫部分也不需要特别的伪装,设置好UA信息,伪装成正常访客就可以了。
小结:
1.编码很重要,一开始爬取的数据解析后中文都乱码了,主要是GBK和UTF-8编码转换的问题;
2.养成写代码解耦分部并且检查的习惯,一开始代码一路写下来,全部是一坨,出问题非常难定位到哪里错了。修改分函数后,每个部分每个功能独立出来,不仅代码看起来直观了,出现问题也变少;
3.基础不够,还是需要继续努力;
最后,通过这次的补考,让我对python的应用有了更进一步的提升,受益良多。