一、PSP表格
PSP | Personal Software Process Stages | 预估耗时(分钟) | 实际耗时(分钟) |
Planning | 计划 | 60 | 80 |
Estimate | 估计这个任务需要多少时间 | 1440 | 1800 |
Development | 开发 | - | - |
Analysis | 需求分析 (包括学习新技术) | 180 | 480 |
Design Spec | 生成设计文档 | 40 | 60 |
Design Review | 设计复审 (审核设计文档) | 40 | 60 |
Coding Standard | 代码规范 (为目前的开发制定合适的规范) | 60 | 30 |
Design | 具体设计 | 60 | 60 |
Coding | 具体编码 | 360 | 480 |
Code Review | 代码复审 | 120 | 180 |
Test | 测试(自我测试,修改代码,提交修改) | 60 | 60 |
Reporting | 报告 | - | - |
Test Report | 测试报告 | 30 | 30 |
Size Measurement | 计算工作量 | 60 | 40 |
Postmortem & Process Improvement Plan | 事后总结, 并提出过程改进计划 | 120 | 120 |
合计 | 2630 | 3480 |
二、任务要求的实现
2.1 项目设计与技术栈
从阅读完题目到完成作业,这一次的任务被你拆分成了几个环节?你分别通过什么渠道、使用什么方式方法完成了各个环节?列出你完成本次任务所使用的技术栈。
- 大致分为四部分。首先,先对题目有大致的理解,抓住关键词中国疫情、爬虫、卫健委官网、每日统计、Excel表格、可视化及每日热点功能
其实内心os:真的要这么难吗…。其次,因为接触爬虫较晚,于是利用csdn(主要参考睿吉吉)等对爬虫和可视化展开了猛烈的进攻,诠释了什么是时间紧任务重。然后就根据所看和所得开始了编写之旅,在最初对卫健委官网数据进行爬取时频频出错于是改变了策略,改爬别的官网。所使用的技术栈:url获取地址、response请求、pyquery提取html中dom数据、pandas将数据生成csv表格以及pyecharts绘制相应图表。
2.2 爬虫与数据处理
说明业务逻辑,简述代码的设计过程(例如可介绍有几个类,几个函数,他们之间的关系),并对关键的函数或算法进行说明。
- 首先是利用import导入了相关的类,然后建立了get_data()来获取相应地址中的数据,并将数据输出为json对象并存储。
def get_data():#获取数据
url = "https://ncov.dxy.cn/ncovh5/view/pneumonia"#获取地址
response = requests.get(url)#请求
if response.status_code == 200:#判断网络请求是否成功
response.encoding = "utf-8"#设置utf-8编码
dom = pq(response.content)#取出各省的数据,转为json对象
data = dom("script#getAreaStat").text().split(" = ")[1].split("}catch")[0] #用来存储数据
jsonObj = json.loads(data) #json对象
print("数据抓取成功")
- 其次利用for语句对访问的地址进行遍历以及数据的获取,成功则导出为csv文件,否则输出相应错误。
province_data = []#定义省份初始值
for item in jsonObj:#遍历相应省份并写入字典
dic = {"省全称": item["provinceName"],
"省简称": item["provinceShortName"],
"现存确诊人数": item["currentConfirmedCount"],
"累计确诊人数": item["confirmedCount"],
"治愈人数": item["curedCount"],
"死亡人数": item["deadCount"]}
province_data.append(dic)#将字典存入省份数据内
if len(province_data) > 0:#判断是否为正常省份名称
print("写入数据")
try:#获取数据
df = pd.DataFrame(province_data)
time_format = time.strftime("%Y-%m-%d_%H_%M_", time.localtime())#输出打印时间
df.to_csv(time_format + "全国各省疫情数据.csv", encoding="gbk", index=False)#转换为csv文件格式输出
print("写入成功")
except Exception as e:#报错
print("写入失败{e}")
2.3 数据统计接口部分的性能改进
记录在数据统计接口的性能上所花费的时间,描述你改进的思路,并展示一张性能分析图(例如可通过VS 2019/JProfiler的性能分析工具自动生成),并展示你程序中消耗最大的函数。
- 利用VSCode对可视化的py文件进行了性能分析如下图,由于未使用VSCode编写过Python代码导致在安装库时浪费较大时间,并且发现进程的内存相对较大。
2.4 每日热点的实现思路
简要介绍实现该功能的算法原理,可给出必要的步骤流程图、数学公式推导和核心代码实现,并简要谈谈所采用算法的优缺点与可能的改进方案。
- 突出了疫情新增的人数,对各省的数据进行分析,利用扇形图和html界面进行展示,核心代码:利用create_Pie()方法构造扇形图,获取各省各市情况,其中os.path子库以path为入口,用于操作和处理文件路径,将每个省份以目录形式打印输出。
def create_Pie(provinceName, dic_citys) -> Pie:
c = (#设置相应的扇形图,宽高,输入写入,时间更新等
Pie(init_opts=opts.InitOpts(width="100%", height="800px", page_title=provinceName + "各市(区)情况"))
.add("", data_pair=list(dic_citys.items()), center=["50%", "58%"], )
.set_global_opts(title_opts=opts.TitleOpts(title=provinceName + "各市(区)情况", subtitle="数据更新于:" + timeformat))
.set_series_opts(label_opts=opts.LabelOpts(formatter="{b}: {c}"))
)
if not os.path.exists('./中国各省情况'):
os.mkdir('./中国各省情况')
c.render("./中国各省情况/" + provinceName + "各市(区)情况.html")
- 优点:直观性强,可直接观看出各市新增数量,同时也可根据图例进行展示。
- 缺点及改进:只能根据每个省市进行查看,突出性不强,可在可塑形方面进行改进,需要加强单独连接到实事链接,更突出展示疫情每日新增确诊人口数。
- 效果展示如下(以福建省为例)。
2.5 爬虫与数据处理
在博客中介绍数据可视化界面的组件和设计的思路。
- 主函数如下,包括获取相应地址中的数据,并将数据输出为json对象并存储在上述文件路径下以及遍历得到各省各市每日的新增情况(以上图福建省为例进行展示)。
if __name__ == '__main__':#主函数
try:
url = "https://ncov.dxy.cn/ncovh5/view/pneumonia"#获取地址
timeformat = time.strftime("%Y-%m-%d %H:%M:", time.localtime())#输出打印时间
response = requests.get(url)#请求
response.encoding = "utf-8"#设置utf-8编码
if response.status_code == 200:#判断网络请求是否成功
dom = pq(response.text)#取出各省的数据,转为json对象
jsonobj = json.loads(dom("script#getAreaStat").text().split(" = ")[1].split("}catch")[0])#用来存储数据
for province in jsonobj:#遍历
dic_city = {}#设置城市初始值
for city in province["cities"]:#遍历省份内的城市并写入
dic_city[city["cityName"]] = city["currentConfirmedCount"]#市名重合
if dic_city.__len__() > 0:#判断是否为正常市名称
create_Pie(province["provinceName"], dic_city)#将省份和市写入
print(province["provinceName"] + "各市数据汇总完毕!")
except Exception as e:#报错
print(e)
- 同时利用map函数对中国国内疫情各省份的确诊人数进行的总展示。利用map_visual_map()方法构造中国地图,利用.add和visual对相应人口展示不同颜色,使确诊人数看起来更直观。
def map_visual_map() -> Map:
c = (
Map(init_opts=opts.InitOpts(page_title="中国疫情地图"))
.add("现存确诊人数", data_pair=list(current_data_dic.items()), maptype="china")
.set_global_opts(
title_opts=opts.TitleOpts(title="中国疫情地图", subtitle="数据更新于" + time_format),
visualmap_opts=opts.VisualMapOpts(pieces=[
{"value": 0, "label": "无", "color": "#9AFF9A"},
{"min": 1, "max": 9, "label": "1~9", "color": "#FFCCCC"},
{"min": 10, "max": 99, "label": "10~99", "color": "#DB5A6B"},
{"min": 100, "max": 499, "label": "100~499", "color": "#FF6666"},
{"min": 500, "max": 999, "label": "500~999", "color": "#CC2929"},
{"min": 1000, "max": 9999, "label": "1000~9999", "color": "#8C0D0D"},
{"min": 10000, "label": ">10000", "color": "#9d2933"}
], is_piecewise=True),
)
)
return c
三、心得体会
- 看到本次编程的第一反应就是好难啊
此处省略部分脏话,然后第一反应就是暴力获取卫健委官网的数据虽然但是好像行不太通,于是开始查找资料搜寻疫情最新消息的官网,在此之前利用了百度的数据,但数据又不太完善,通过csdn和bilibili查看相关的源代码和教程,最终利用了丁香园的数据。卫健网真的很难爬,知识储备有限转变策略。 - 同时通过这次作业,理解与学习了python从命令行执行程序并读取参数、正则表达式的使用、单元测试、性能分析等基本操作,同时,在本次作业之前从未使用过GitHub,也学会将本地仓库与远程的 GitHub 仓库关联起来。但也有很大的问题,比如对代码运用的不熟练,脑子里有想法但做不出东西,需要查阅相关资料,也是初次使用VSCode对代码进行性能分析。