• 结对第二次作业


    这个作业属于哪个课程
    https://edu.cnblogs.com/campus/fzu/2020SpringW/
    这个作业要求在哪里
    https://edu.cnblogs.com/campus/fzu/2020SpringW/homework/10456
    结对学号
    221701429 221701438
    这个作业的目标
    疫情统计可视化的原型
    作业正文
    ....
    其他参考文献
    ....

    一、Github 仓库地址和代码规范链接

    二、成品演示

    • 地图上方提供日历,可以选取不同日期查看截止该日全国疫情情况
      conv_ops

    • 统计数据在地图上方,只显示到助教提供的静态文件最后一个日期
      相同感染人数区间的省份可以通过左下方鼠标停留或点击
      conv_ops

    • 全国疫情折线图在地图下方,可选择显示或隐藏确诊,疑似,治愈,死亡四条折线
      折线上的点显示当前日期的疫情数据
      conv_ops

    • 地图上点击不同省份会跳转到该省份疫情数据的折线图
      conv_ops

    三、结对讨论过程描述

    • 作业发布当天晚上,由于技术不足无法实现实时数据更新,我们决定用javeEE课上学的JSP框架和数据库完成本次作业
      聊天1
      聊天2

    四、描述设计实现过程

    221701429-前端

    • 作业题目有提示用echarts设计图表,就跟着学了echarts的教程,下载了文件,
    在前端用jsp的方式实现页面,在页面中加入script,添加图表,设置图表的类型和参数,就能够显示出来了。
    数据部分则是通过Servlet的http请求获取的,把数据库中的表的数据实例化成Province后,通过req.setAttribute的方式传递参数。
    在地图上设置了点击事件,将params加到url上传递给Servlet判断,点击后跳转到具体省份的疫情的功能就实现了。

    前端

    221701438-后端

    • 与前端交流后,确定我的主要任务是对log文件夹下的日志进行处理,再将日志中数据写入数据库,完善疫情数据的读取和存储。
    结合之前所学,我将每个省份的疫情情况封装在Province类,把助教提供的静态日志内容读取出来,存储在ArrayList<Province>
    再用正则匹配将每个省的疫情数据提取并写入数据库,然后完善数据库的存取。

    后端

    五、关键代码

    • Jsp页面通过http请求获得Servlet传的数据,用div的方式显示出来,在css中更改样式使得四块横向排版。
    <div id="virusSummary">
        <%
            int totalip = (int) request.getAttribute("totalip");
            int totalsp = (int) request.getAttribute("totalsp");
            int totalcure = (int) request.getAttribute("totalcure");
            int totaldead = (int) request.getAttribute("totaldead");
        %>
        <div id="ip">
            <div class="name">确诊</div>
            <div class="data"><%=totalip%></div>
        </div>
        <div id="sp">
            <div class="name">疑似</div>
            <div class="data"><%=totalsp%></div>
        </div>
        <div id="cure">
            <div class="name">治愈</div>
            <div class="data"><%=totalcure%></div>
        </div>
        <div id="dead">
            <div class="name">死亡</div>
            <div class="data"><%=totaldead%></div>
        </div>
    </div>
    
    • 这是用echarts实现疫情地图的script,tooltip改变数据提示框的输出格式,visualMap改变确诊人数区间对应的颜色提示,series里data部分填入http请求得到的确诊人数数据,然后显示到地图上。再添加一个function点击事件,点击省份后跳转到该省份的疫情折线图的页面。
    <div id="chinaMap"></div>
    <script type="text/javascript">
        var myChart = echarts.init(document.getElementById('chinaMap'));
            myChart.setOption({
                // 数据提示框
                tooltip: {
                    trigger: 'item', // item放到数据区域触发
                    formatter: '地区:{b}<br/>确诊:{c}' // 提示数据格式br表示换行,地图 : {a}(系列名称),{b}(区域名称),{c}(合并数值), {d}(无)
                },
                // 工具栏
                /*toolbox: {
                    show: true,
                    orient: 'horizontal',
                    left: 'right',
                    feature: {
                        dataView: {readOnly: false},
                        restore: {},
                        saveAsImage: {}
                    }
                },*/
    
                // 使用透明度来区分疫情严重情况
                visualMap: {
                    type: 'piecewise',
                    pieces: [
                        {gt: 1500, color: 'darkred'},
                        {gt: 1000, lte: 1500, color: 'red', colorAlpha: 1},
                        {gt: 500, lte: 1000, color: 'red', colorAlpha: 0.8},
                        {gt: 300, lte: 500, color: 'red', colorAlpha: 0.6},
                        {gt: 100, lte: 300, color: 'red', colorAlpha: 0.4},
                        {gt: 50, lte: 100, color: 'red', colorAlpha: 0.3},
                        {gt: 0, lte: 50, color: 'red', colorAlpha: 0.2},
                        {lte: 0, color: 'white'}
                    ],
                },
    
    
                // 具体数据
                series: [
                    {
                        name: '各省确诊病例', // 系列名称
                        type: 'map', // 系列类型,地图
                        map: 'china', // 要使用的地图,即上面注册的地图名称
                        //roam: true, // 开启鼠标缩放和平移漫游
                        label: { // 图形上的文本标签,地图默认显示数据名
                            show: true,
                            formatter: '{b}', // b是数据名,c是数据值
                            fontSize: 12
                        },
                        data:[
                            <%
                            int Ip;
                            for(int i = 0; i < ProvinceName.provinceSize; i++){
                                //ip = 0;
                                Ip = (int) request.getAttribute(ProvinceName.provinceName[i] + "Ip");
                            %>
                            {name: "<%=ProvinceName.provinceName[i]%>", value: "<%=Ip%>"},
                            <%}%>
                        ]
                    }
                ]
            });
    
        //点击省份后跳转到具体疫情的页面
        myChart.on("click",function (params) {
            window.location.href = "Servlet?flag=2&name="+params.name;
        },true)
    </script>
    
    • 该部分显示的是全国四种人数的折线图,用echarts定制的折线图样式,将获取的日期作为xAxis的数据、四种人数作为每个点的值,实现折线图。点击省份进入具体页面的折线图与之类似。
    <div id="lineChart" style=" 800px;height:400px; position: center; background-color: #ffffff; padding-top: 40px"></div>
    <script type="text/javascript">
    
        var name = "全国";
        // 基于准备好的dom,初始化echarts实例
        var Chart = echarts.init(document.getElementById('lineChart'),'infographic');
    
        Chart.setOption({
            //设置标题
            title: {
                text: name + '疫情趋势'
            },
            //数据提示框
            tooltip: {
                trigger: 'axis',
            },
            legend: {
                data: ['确诊','疑似','治愈','死亡']
            },
            xAxis: {
                data:[<%
                  List<Province> country = (List<Province>) request.getAttribute("country");
                  String date;
                  int ip,totalIp = 0;
                  int sp,totalSp = 0;
                  int cure,totalCure = 0;
                  int dead,totalDead = 0;
                  for(Province province : country){
                      date = province.getDate();
                  %>
                    "<%=date%>",
                    <%}%>]
            },
            yAxis: {},
            series: [
                {
                    name: '确诊',
                    type: 'line',
                    data:[<%
                      for(Province province : country){
                          ip = province.getIp();
                          totalIp += ip;
                      %>
                        <%=totalIp%>,
                        <%}%>]
                },
                {
                    name: '疑似',
                    type: 'line',
                    data:[<%
                      for(Province province : country){
                          sp = province.getSp();
                          totalSp += sp;
                      %>
                        <%=totalSp%>,
                        <%}%>]
                },
                {
                    name: '治愈',
                    type: 'line',
                    data:[<%
                      for(Province province : country){
                          cure = province.getCure();
                          totalCure += cure;
                      %>
                        <%=totalCure%>,
                        <%}%>]
                },
                {
                    name: '死亡',
                    type: 'line',
                    data:[<%
                      for(Province province : country){
                          dead = province.getDead();
                          totalDead += dead;
                      %>
                        <%=totalDead%>,
                        <%}%>]
                }
            ]
        },true)
    </script>
    
    • Servlet控制前后端数据交互,调用对象类实例化,将参数通过http请求发送给下一个页面,通过url附带参数的形式,在Servlet中获取参数并判断选择进入的页面。
    String flag = req.getParameter("flag");
    ProvinceDAO provinceDAO =new ProvinceDAOImpl();
    //flag=2时跳转到第二个页面
    if(flag != null && flag.equals("2")){
        String name = req.getParameter("name");
        provinceDAO =new ProvinceDAOImpl();
        List<Province> local = provinceDAO.list(name,true);//获取当地每天数据
        int ip = 0,sp = 0,cure = 0,dead = 0;
        //累加当地每天的数据
        for (Province province : local) {
            ip += province.getIp();
            sp += province.getSp();
            cure += province.getCure();
            dead += province.getDead();
        }
        req.setAttribute("name",name);
        req.setAttribute("totalip",ip);
        req.setAttribute("totalsp",sp);
        req.setAttribute("totalcure",cure);
        req.setAttribute("totaldead",dead);
        req.setAttribute("local",local);
        req.getRequestDispatcher("concreteInfectStatistic.jsp").forward(req,resp);
    }
    //否则跳转到第一个页面
    else{
        provinceDAO =new ProvinceDAOImpl();
        List<Province> country = provinceDAO.list("全国",true);//获取全国每天数据
        //List<Province> all = provinceDAO.list();//获取各省份每天的数据
        int ip = 0,sp = 0,cure = 0,dead = 0;
        //累加全国每天的数据
        for (Province province : country) {
            ip += province.getIp();
            sp += province.getSp();
            cure += province.getCure();
            dead += province.getDead();
        }
    
        String name;
        int eachIp;
        //查找每个省份的每天的确诊数据累加到一个数值上
        for(int i = 0; i < ProvinceName.provinceSize; i++) {
            name = ProvinceName.provinceName[i];
            eachIp = 0;
            List<Province> each = provinceDAO.list(name, true);//按省份名获取省份每天数据
            for(Province province : each){
                eachIp += province.getIp();
            }
            req.setAttribute(name+"Ip",eachIp);
        }
        req.setAttribute("totalip",ip);
        req.setAttribute("totalsp",sp);
        req.setAttribute("totalcure",cure);
        req.setAttribute("totaldead",dead);
        req.setAttribute("country",country);
    
    
        req.getRequestDispatcher("chinaMap.jsp").forward(req,resp);
    }
    
    • 读取目录下指定日期前的所有日志内容
     public static String[] readFile(String path,String date) throws ParseException, IOException {
            List allFilePath = getFileName(path,date);
            String[] allContent = new String[allFilePath.size()];
            for (int i = 0; i < allFilePath.size(); i++){
                File file = new File(String.valueOf(allFilePath.get(i)));
                StringBuilder result = new StringBuilder();
                // 构造一个BufferedReader类来读取文件
                BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream(file),"UTF-8"));
                String s;
                // 使用readLine方法,一次读一行,并忽略注释行
                while ((s = br.readLine()) != null && !s.startsWith("//")) {
                    result.append(System.lineSeparator() + s);
                }
                br.close();
                allContent[i] = result.toString();
            }
            return allContent;
        }
    
    • 将正则匹配处理完的数据填入数据库
     public static void connectMysql() throws IOException, ParseException {
            for (int i=0; i<date.length; i++){
                String[] allContent = readFile("src/infectstatistic/log",date[i]);
                ArrayList<Province> province = RegularMatch.match(allContent);
                ListAdd(province, date[i]);
            }
        }
    

    六、《构建之法阅读心得》、心路历程和收获及对队友的评价

    阅读心得

    • 构建之法第四章提到两人合作开发,我和队友采用的是前后端分离的,按照作业要求使用Git分支,建立一条dev分支,让队友和自己在dev分支上开发,开发结束后再合并到main分支。第一次接触这样的结对编程,感到新颖的同时也很陌生,相信在以后的实践中对这种合作开发会有更多经验。
    • 第五章讲述软件团队模式和开发流程,至于团队模式和团队的开发模式的关系,我个人的理解是一群人在一起做软件开发,总是要一些方式方法。而这里团队模式就是这一群人的定性,团队的开发模式则是这群人使用的方法的定性。

    心路历程

    221701429
    • 刚开始以为实现地图会很难,但是知道了echarts之后发现也没有那么难实现,
      就是设置图表格式和传入数据的事情,折线图也是一个意思。收获也是挺多的,
      第一次写前端页面,一直设置不好,没办法做出自己想要的样子,甚是苦恼,
      但时间问题也只能作罢,美名其曰“精简”。
      这次结对作业锻炼了我们的合作开发能力,对技术上的也好、配合上的也好,
      都有很大的提升,对GitHub的使用也更熟练了一些,总的来说是一件好事。
      成长总是要经历一些挫折的,这也是我的感受。
    221701438
    • 第一次看到这次作业感觉非常难,毕竟自己很少接触前后端分离的开发模式,
      与队友讨论完也认清自己的任务,代码虽然不多,但是小BUG还是很多,
      因为自己能力不足,很多时候还是在查文档和看大佬代码中学习。
      本次结对作业采用了全新的结对开发模式,刚上手不是很熟悉,
      在查找很多资料后逐渐掌握,这也算学到一种新的技能。

    对队友的评价

    221701429
    • 他是个靠谱的队友,能一起合作是我的荣幸,他的部分我完全不用担心,
      都能做好,对前端的部分也能提出一些建议,是个有实力有配合的队友。
    221701438
    • 我的队友代码规范,对本次作业的看法很多很棒,能给后端很清晰的开发思路。
  • 相关阅读:
    Django动态渲染多层菜单
    python使用pdkdf2加盐密码
    ceil 模块
    python面试总结
    Django 中related_name,"%(app_label)s_%(class)s_related"
    安装zabbix-3.0.3+nginx-1.10.1+php-5.6.22
    Django 权限管理
    python RecursionError: maximum recursion depth exceeded in comparison错误
    django _meta方法
    html 之input标签height设置问题
  • 原文地址:https://www.cnblogs.com/hxd1017/p/12488967.html
Copyright © 2020-2023  润新知