py爬取疫情数据并存入mysql,web展示数据

长这么大没见过有这种作业,比实训还是实训。

需求:

1.爬取疫情相关数据,用疫情api或者官网都可以,语言不限

2.最好能够持久化数据,存入数据库

3.用网页展示每个省份的疫情数据

4.最好能够“输入想要查询的省份,就能以图表的形式动态展示”

想法:

1.java爬取?不不不,太难了,用python爬

2.python爬到的数据库存入mysql数据库,故需要提前准备好字段

3.图表python可以生成,but第四个需求实现貌似有些麻烦,需要python脚本植入网页,才能动态生成图表。emm,网上查询了一下,可以用echarts,在Javascript里头写。

4.图表和数据都可以在网站上显示,后端就用springboot吧,刚自学完,顺便练练手,前端可以用element快速生成。

实现:

1.py爬取并存入数据库

我采用的是网易的疫情api:接口

打开一看。。。巨乱,but可以在官网上,按f12打开开发者工具看标签,舒服多了。

根据右边的东东,可以拿到好多国家的每天确诊、死亡、治愈数据,也可以拿到国内省份的总计数据和当天数据。

我这里需要拿到省份的总计数据和当天数据,children里面是所有省份的数据。

密密麻麻都是数据,上图显示的台湾的数据,total是总计数据,today是今日数据,里头分别有confirm、dead、heal,是确诊、死亡、治愈的意思。

py中举几个例子:

json_data = response.json()['data']['areaTree'][2]['children'][0] # 中国省份数据
proData = json_data[0]  # 台湾的数据
today_confirm = json.dumps(proData['today']['confirm'])  # 今日确诊数
today_confirm = json.dumps(proData['total']['heal'])  # 总计治愈数

我的sql表是酱紫的:

打开pycharm,导包,有些是之前在python做图表用的

import requests #爬取网页
import json #json文件可以通过角标索引读取内容 爬取json文件
import time
import pymysql
import matplotlib.pyplot as plt
from pylab import mpl

 在导包下方加入这两行,因为后面要的数据有省份名,显示成unicode编码,加入这两句可以解决。

# 设置显示中文字体
mpl.rcParams["font.sans-serif"] = ["SimHei"]
# 设置正常显示符号
mpl.rcParams["axes.unicode_minus"] = False

 再加入这几行,前三行是用于模拟人上网站用的,后两句是用于存入mysql数据库用的,数据库名字和密码自行更替。

url = 'https://c.m.163.com/ug/api/wuhan/app/data/list-total?t=329822670771' #请求URL
headers = {'user-agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/97.0.4692.71 Safari/537.36 Edg/97.0.1072.55'} #浏览器访问
response = requests.get(url , headers = headers)

db = pymysql.connect(host='localhost', port=3306, user='root', passwd='1234', db='yiqing', charset='utf8')
cursor = db.cursor()

写个函数用于爬取

def toDay():
    json_data = response.json()['data']['areaTree'][2]['children']  # 中国省份数据
    for i in range(34):  # 网页数据显示共有0-33个省份
        proData = json_data[i]  # 每个省份的数据
        add = eval(
            json.dumps(proData['name']).encode('utf-8').decode('unicode_escape'))  # 省份名,unicode转化为utf-8,去掉两端引号,真累 l_l
        today_confirm = json.dumps(proData['today']['confirm'])  # 确诊数目
        today_dead = json.dumps(proData['today']['dead'])  # 死亡数
        today_heal = json.dumps(proData['today']['heal'])  # 治疗数
        # print("省份:"+add+",确诊:"+today_confirm+",治疗:"+today_heal+",死亡:"+today_dead)#今日日期

写个函数用于插入当天数据

def insertDB(add, confirm, dead, heal):
    try:
        date = time.strftime("%m月%d日", time.localtime(time.time()))
        sql = "insert into trend (province,today_confirm,today_dead,today_heal,date) values('%s',%s,%s,%s,'%s')" % (
        add, confirm, dead, heal, date)
        cursor.execute(sql)
        db.commit()
    except Exception as e:
        db.rollback()
        print(e)

写个函数查询数据库,根据省份名查询该省份的每一天疫情情况,后面注释的画表的,有兴趣自己玩玩

def find(add):
    sql = "select * from trend where province='"+add+"'"
    cursor.execute(sql)
    rs=cursor.fetchall()
    print(rs)
    confirm = []
    dead = []
    heal = []
    data = []

    for i in range(len(rs)):
        if(rs[i][1]==add):
            confirm.append(rs[i][2])
            dead.append(rs[i][3])
            heal.append(rs[i][4])
            data.append(rs[i][5])
    print(confirm)
    print(dead)
    print(heal)
    print(data)

    # plt.plot(data, confirm,ls='dotted', lw=2,label='确诊人数',color='blue')
    # plt.plot(data, dead, ls='dotted', lw=2,label='滴答人数',color='red')
    # plt.plot(data, heal, ls='dotted', lw=2,label='治愈人数',color='green')
    # # plt.plot(1, 4, 9, 16, 25)
    #
    # # 设置图标标题,并给坐标轴加上标签
    # title = add+"近期疫情数据"
    # plt.title(title, fontsize=24)
    # plt.xlabel("日期", fontsize=20)
    # plt.ylabel("人头数", fontsize=20)
    # plt.legend(prop={'family':'SimHei', 'size':14})
    # # 设置刻度标记的大小
    # plt.tick_params(axis='both', labelsize=8)
    # plt.axis([0, 4, 0, 15])
    # plt.show()

py代码全部奉上

import requests #爬取网页
import json #json文件可以通过角标索引读取内容 爬取json文件
import time
import pymysql
import matplotlib.pyplot as plt
from pylab import mpl
# 设置显示中文字体
mpl.rcParams["font.sans-serif"] = ["SimHei"]
# 设置正常显示符号
mpl.rcParams["axes.unicode_minus"] = False
url = 'https://c.m.163.com/ug/api/wuhan/app/data/list-total?t=329822670771' #请求URL
headers = {'user-agent' : 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/97.0.4692.71 Safari/537.36 Edg/97.0.1072.55'} #浏览器访问
response = requests.get(url , headers = headers)

db = pymysql.connect(host='localhost', port=3306, user='root', passwd='1234', db='yiqing', charset='utf8')
cursor = db.cursor()

# print(response.status_code) #200表示访问成功
# print(response.json()) # 打印内容

def insertDB(add, confirm, dead, heal):
    try:
        date = time.strftime("%m月%d日", time.localtime(time.time()))
        sql = "insert into trend (province,today_confirm,today_dead,today_heal,date) values('%s',%s,%s,%s,'%s')" % (
        add, confirm, dead, heal, date)
        cursor.execute(sql)
        db.commit()
    except Exception as e:
        db.rollback()
        print(e)



def insertDB(add,confirm,dead,heal,flag):
    # 插入省份一天的数据
    if(flag==1):
        try:
            date = time.strftime("%m月%d日", time.localtime(time.time()))
            sql = "insert into trend (province,today_confirm,today_dead,today_heal,date) values('%s',%s,%s,%s,'%s')" % (add, confirm, dead, heal, date)
            cursor.execute(sql)
            db.commit()
        except Exception as e:
            db.rollback()
            print(e)
    else:
        try:
            sql = "update  situation set   total_confirm = '%s',total_dead = '%s',total_heal = '%s' where province = '%s' " % (confirm, dead, heal, add)
            cursor.execute(sql)
            db.commit()
        except Exception as e:
            db.rollback()
            print(e)


def toDay():
    json_data = response.json()['data']['areaTree'][2]['children']  # 中国省份数据
    for i in range(34):  # 网页数据显示共有0-33个省份
        proData = json_data[i]  # 每个省份的数据
        add = eval(
            json.dumps(proData['name']).encode('utf-8').decode('unicode_escape'))  # 省份名,unicode转化为utf-8,去掉两端引号,真累 l_l
        today_confirm = json.dumps(proData['today']['confirm'])  # 确诊数目
        today_dead = json.dumps(proData['today']['dead'])  # 死亡数
        today_heal = json.dumps(proData['today']['heal'])  # 治疗数
        # print("省份:"+add+",确诊:"+today_confirm+",治疗:"+today_heal+",死亡:"+today_dead)#今日日期
        insertDB(add, today_confirm, today_dead, today_heal,1)

def toTotal():
    json_data = response.json()['data']['areaTree'][2]['children']  # 中国省份数据
    for i in range(34):  # 网页数据显示共有0-33个省份
        proData = json_data[i]  # 每个省份的数据
        add = eval(
            json.dumps(proData['name']).encode('utf-8').decode('unicode_escape'))  # 省份名,unicode转化为utf-8,去掉两端引号,真累 l_l
        today_confirm = json.dumps(proData['total']['confirm'])  # 确诊数目
        today_dead = json.dumps(proData['total']['dead'])  # 死亡数
        today_heal = json.dumps(proData['total']['heal'])  # 治疗数
        insertDB(add, today_confirm, today_dead, today_heal, 2)
def find(add):
    sql = "select * from trend where province='"+add+"'"
    cursor.execute(sql)
    rs=cursor.fetchall()
    print(rs)
    confirm = []
    dead = []
    heal = []
    data = []

    for i in range(len(rs)):
        if(rs[i][1]==add):
            confirm.append(rs[i][2])
            dead.append(rs[i][3])
            heal.append(rs[i][4])
            data.append(rs[i][5])
    print(confirm)
    print(dead)
    print(heal)
    print(data)

    # plt.plot(data, confirm,ls='dotted', lw=2,label='确诊人数',color='blue')
    # plt.plot(data, dead, ls='dotted', lw=2,label='滴答人数',color='red')
    # plt.plot(data, heal, ls='dotted', lw=2,label='治愈人数',color='green')
    # # plt.plot(1, 4, 9, 16, 25)
    #
    # # 设置图标标题,并给坐标轴加上标签
    # title = add+"近期疫情数据"
    # plt.title(title, fontsize=24)
    # plt.xlabel("日期", fontsize=20)
    # plt.ylabel("人头数", fontsize=20)
    # plt.legend(prop={'family':'SimHei', 'size':14})
    # # 设置刻度标记的大小
    # plt.tick_params(axis='both', labelsize=8)
    # plt.axis([0, 4, 0, 15])
    # plt.show()

# toTotal()
# toDay()
find('广东')
# print(json_data)

2.来写个springboot后端。(代码后面发)

这是目录结构

 用springboot快速搭建,maven用阿里的镜像,jdk用8,选择需要用到的包。

mybatis-plus(官网的url应该还不支持),web,mysql,lombok(省掉set、get和构造方法)

 

 第一步写domain实体类,两个表对应的实体类都写

字段名写一样需要关闭mp的驼峰命名法,不然找不到对应字段。再applicationContext.yaml里写,自己创建新的。

 顺便把mysql数据库参数设置以下,因为我创建的boot工程里就写好了模板,所以就再applicationContext.properties里写。

 接着分别编写dao,service类。

dao继承BaseMapper的,直接用就可以了;service需要写个接口和实现类,目录参考前面的。

Situation对应的dao和service也一样,就不举例子了。 

 写完单元测试一下,试试查询数据行不行。

没问题的话,写写controller类,我懒一点,一个controller大家用。

 写完controller,运行入口Application类,然后去postman测试下。

 查询各个省份总计情况

 查询某个省份每天情况。

 都没得问题。

3.写前端网页,用element组件库来写,省心省力。

找到对应的布局容器,复制粘贴。

aside用竖的导航菜单,复制粘贴。每个item的图标和文字自行定义,element给了一大堆图标

main区域,放个表格,复制粘贴。表格内用后端查询到的数据存放。

 

左边导航菜单有三个,提前设置三个div, 默认显示第一个,其他两个都取消显示。

点击某个时,当前显示,其他不显示。

左边三个div里面无非就显示controller传送过来的数据,这里用到异步,我用axios。

 这里的addDate需要提前定义好,然后将addDate和表格进行双向绑定,表格就可以显示数据啦。

 

拿到想要的数据,就可以作图了,echarts作图需要横坐标,纵坐标,数据(x,y)

我作图再js里完成,把前面vue获取的数据拿过来,用数组存放确诊,死亡,治愈,日期。

设置图表放在哪个地方,需要提前定义好div,设置宽高。

将dom对象让echarts初始化。 

 接着就是画图了

 画出来的图,默认如下,当然可以做的很漂亮。

如果用到多组数据,就在series里面多写几组,series的type是可以是折线图,饼状图,柱形图。echarts功能很强大,颜色,形状,样式都可以设置。

 提取码:qtnb

 

 

 

 

 

  • 5
    点赞
  • 41
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值