福州大学软件工程实践个人编程作业

这个作业属于哪个课程 https://edu.cnblogs.com/campus/fzu/SE2020
这个作业要求在哪里 https://edu.cnblogs.com/campus/fzu/SE2020/homework/11167
这个作业的目标 github的使用;json解析
学号 031802520

目录

·PSP表格
·解题思路
·设计实现过程
·代码说明
·单元测试
·单元测试覆盖率优化
·性能优化
·代码规范链接
·总结

PSP表格

PSP2.1 Personal Software Process Stages 预估耗时(分钟) 实际耗时(分钟)
Planning 计划 60 90
Estimate 估计这个任务需要多少时间 30 30
Development 开发 120 180
Analysis 需求分析 240 250
Design Spec 生成设计文档 30 30
Design Review 设计复审 30 60
Coding Standard 代码规范 5 10
Design 具体设计 30 50
Coding 具体编码 120 240
Coding Review 代码复审 40 60
Test 测试 30 60
Reporting 报告 30 60
Test Report 测试报告 20 20
Size Measurement 计算工作量 50 60
Postmortem & Process Improvement Plan 总结, 思考如何优化 50 60
合计 885 1230

解题思路

然后看了这题感觉无从下手,就先学习老师的b站视频,学习到基本的git的使用。问了问大佬,了解了这题是要解析json。样例代码给的
是python,大佬也说python写起来方便,可是菜鸡如我只会C++。同学推荐我用慕课网上的免费文字课程,于是从0开始学习python。学
习了用递归遍历文件夹后取文件逐行解析。对于数据分析,同学建议用正则表达式的匹配优化。对于示例程序的递归展开部分运行了许多
冗余信息,直接遍历搜索更快。

设计实现过程

代码说明

注:说明在注释当中

# -*- coding: utf-8 -*-
import os
import argparse
import pickle
import re

DATA = ("PushEvent", "IssueCommentEvent", "IssuesEvent", "PullRequestEvent" )
    # 匹配时使用
pattern = re.compile(r'"type":"(\w+?)".*?actor.*?"login":"(\S+?)".*?repo.*?"name":"(\S+?)"')
    # 正则表达式的使用,优化匹配速度

  class Data:
    def __init__(self):
        self._user = {}
        self._repo = {}
        self._user_repo = {}
    # 初始化记录读取的内存
    # 可使函数无参使用

    @staticmethod
    def __parse(file_path: str):

         records = []
        # 打开json文件
        with open(file_path, 'r', encoding='utf-8') as f:
            for line in f:
                # 运用正则表达式匹配有效数据
                res = pattern.search(line)
                if res is None or res[1] not in DATA:
                    continue
                records.append(res.groups())
        return records

    def init(self, dir_path: str):
        records = []
        # 跑目录
        for cur_dir, sub_dir, filenames in os.walk(dir_path):
            filenames = filter(lambda r: r.endswith('.json'), filenames)
            for name in filenames:
            records.extend(self.__parse(f'{cur_dir}/{name}'))

        for record in records:
            event, user, repo = record
            # 取值或创建
            self._user.setdefault(user, {})
            self._user_repo.setdefault(user, {})
            self._repo.setdefault(repo, {})
            self._user_repo[user].setdefault(repo, {})
            self._user[user][event] = self._user[user].get(event, 0)+1
            self._repo[repo][event] = self._repo[repo].get(event, 0)+1
            self._user_repo[user][repo][event] = self._user_repo[user][repo].get(event, 0)+1

            with open('1.json', 'wb') as f:
            pickle.dump(self._user, f)
            with open('2.json', 'wb') as f:
            pickle.dump(self._repo, f)
            with open('3.json', 'wb') as f:
            pickle.dump(self._user_repo, f)

    def load(self):
        if not any((os.path.exists(f'{i}.json') for i in range(1, 3))):
            raise RuntimeError('error: data file not found')

        with open('1.json', 'rb') as f:
            self._user = pickle.load(f)
        with open('2.json', 'rb') as f:
            self._repo = pickle.load(f)
        with open('3.json', 'rb') as f:
            self._user_repo = pickle.load(f)

    def get_user(self, user: str, event: str) -> int:
        return self._user.get(user, {}).get(event, 0)

    def get_repo(self, repo: str, event: str) -> int:
        return self._repo.get(repo, {}).get(event, 0)

    def get_user_repo(self, user: str, repo: str, event: str) -> int:
        return self._user_repo.get(user, {}).get(repo, {}).get(event, 0)
  class Run:
    # 参数设置
    def __init__(self):
        self.parser = argparse.ArgumentParser()
        self.data = None
        self.arg_init()
    # 设置可能有的参数,便于解析

    def arg_init(self):
        self.parser.add_argument('-i', '--init', type=str)
        self.parser.add_argument('-u', '--user', type=str)
        self.parser.add_argument('-r', '--repo', type=str)
        self.parser.add_argument('-e', '--event', type=str)

    def analyse(self):
        args = self.parser.parse_args()

        self.data = Data()
        if args.init:
            self.data.init(args.init)
            return 'init done'
        self.data.load()

        if not args.event:
            raise RuntimeError('error: the following arguments are required: -e/--event')
        if not args.user and not args.repo:
            raise RuntimeError('error: the following arguments are required: -u/--user or -r/--repo')

        # 判断询问
        if args.user and args.repo:
            res = self.data.get_user_repo(args.user, args.repo, args.event)
        elif args.user:
            res = self.data.get_user(args.user, args.event)
        else:
            res = self.data.get_repo(args.repo, args.event)
        return res

  if __name__ == '__main__':
    a = Run()
    print(a.analyse())

单元测试

单元测试覆盖率优化

性能优化

正则表达式的匹配优化
对于冗余数据的不处理

代码规范链接

代码规范点这里

总结

这次的作业对于我而言,是非常难的,平时码的都是算法题,
没有任何开发经验,从最开始有点无从下手,慢慢摸索直至
走上正轨。学习的过程中可以多多询问他人,这样事半功倍。
这次的作业让我明白,还有很多的东西要学,目前的知识还
是太匮乏了。

posted @ 2020-09-16 23:04  FZU_LH  阅读(148)  评论(1编辑  收藏  举报