AI智能
改变未来

2020春软件构造Lab3 Reusability and Maintainability Oriented Programming

Reusability and Maintainability Oriented Programming

  • 1 实验目标概述
  • 2 实验环境配置
  • 3 实验过程
  • 3.1 待开发的三个应用场景
  • 3.2 面向可复用性和可维护性的设计:PlanningEntry
  • 3.2.1 PlanningEntry的共性操作
  • 3.2.2 局部共性特征的设计方案
    • 3.2.3 面向各应用的PlanningEntry子类型设计(个性化特征的设计方案)
  • 3.3 面向复用的设计:R
  • 3.4 面向复用的设计:Location
  • 3.5 面向复用的设计:Timeslot
  • 3.6 面向复用的设计:EntryState及State设计模式
  • 3.7 面向应用的设计:Board
  • 3.8 Board的可视化:外部API的复用
  • 3.9 PlanningEntryCollection的设计
  • 3.10 可复用API设计及Façade设计模式
    • 3.10.1 检测一组计划项之间是否存在位置独占冲突
    • 3.10.2 检测一组计划项之间是否存在资源独占冲突
    • 3.10.3 提取面向特定资源的前序计划项
  • 3.11 设计模式应用
    • 3.11.1 Factory Method
    • 3.11.2 Iterator
    • 3.11.3 Strategy
  • 3.12 应用设计与开发
  • 3.13 基于语法的数据读入
  • 3.14 应对面临的新变化
    • 3.14.1 变化1
    • 3.14.2 变化2
    • 3.14.3 变化3
  • 3.15 Git仓库结构
  • 4 实验进度记录
  • 5 实验过程中遇到的困难与解决途径
  • 1 实验目标概述

    本次实验覆盖课程第 3、4、5 章的内容,目标是编写具有可复用性和可维护性的软件,主要使用以下软件构造技术:
     子类型、泛型、多态、重写、重载
    继承、代理、组合
     常见的 OO 设计模式语法驱动的编程、正则表达式
     基于状态的编程
     API设计、API复用
    本次实验给定了五个具体应用(高铁车次管理、航班管理、操作系统进程管理、大学课表管理、学习活动日程管理),学生不是直接针对五个应用分别编程实现,而是通过 ADT 和泛型等抽象技术,开发一套可复用的 ADT 及其实现,充分考虑这些应用之间的相似性和差异性,使ADT有更大程度的复用(可复用性)和更容易面向各种变化(可维护性)。

    2 实验环境配置

    ●建立本地git仓库
    cd D:\\eclipse-workspace\\Lab3_1180300621
    d:
    dir
    git init //生成.git目录
    git add * //该目录下所有文件纳入git管理【文件->暂存区】
    git status //具体信息
    git commit -m “v0.1 All code in main()” //创建待提交的数据结构【暂存区->本地仓库】
    git log //查看提交信息
    git remote add origin “仓库地址”
    git push -u -f origin master【本地仓库->线上仓库】
    ————————————————————————————————
    ●在这里给出你的GitHub Lab3仓库的URL地址(Lab3-学号)。

    3 实验过程

    3.1 待开发的三个应用场景

    列出你所选定的三个应用。
    ●航班管理
    ●高铁车次管理
    ●学习日程管理
    分析三个应用场景的异同,理解需求:它们在哪些方面有共性、哪些方面有差异。
    ●时间可在创建时设定;
    ●只有学习日程的位置可更改;
    ●只有高铁的状态可阻塞
    ●航班为单个资源、高铁为多个有序资源、学习日程为多个无序资源
    ————————————————————————————————

    3.2 面向可复用性和可维护性的设计:PlanningEntry

    航班·计划项 资源 单个可区分,单架飞机
    飞机·类 编号 string
    机型 string
    座位数 int
    机龄 double
    地点·类(可设定、不可更改) 起点
    经停站
    终点
    时间·类(可设定) 一个起止时间对
    状态(不可阻塞) waiting:航班信息确定、未分配飞机;allocated:已分配飞机、未起飞;running:航班已起飞;ended:航班已抵达;cancelled:航班未起飞前被取消,不再执飞
    高铁·计划项 资源 多个带次序可区分资源,车厢的集合(动车组)
    车厢·类 唯一编号 string
    类型 string
    定员数 int
    使用时长 double
    地点·类(可设定、不可更改) 起点
    一组中间位置
    终点
    时间·类(可设定) 一组起止时间对
    状态(可阻塞) waiting:航班信息确定、未分配车厢;allocated:已分配一组车厢、未发车;running:已从起始站发车;blocked:抵达某个中间站,停ended:高铁已抵达;cancelled:高铁未发车前被取消/或在某个中间站被取消
    活动·计划项 资源 多个不带次序、不需区分ID的资源(如100份学习资料)
    学习材料·类 材料名称 string
    发布部门 string
    发布日期 int(1976 02 06)
    位置·类(可设定、可更改) 一个具体位置
    时间·类(可初始设定) 一个起止时间对
    状态(可阻塞) waiting:建立了学习活动,确定了时间地点;allocated:为活动安排了学习材料;running:开始学习活动;ended:结束学习活动;cancelled:学习活动结束前被取消

    3.2.1 PlanningEntry的共性操作

    能够返回指定类型的PlanningEntry实现类,Flight Schedule为例:



    RUNNING状态在已分配资源之后未启动之前,首先检查是否分配资源(飞机),打印出状态;若已分配资源且状态不为ALLOCATED,则更新航班信息,将状态置为RUNNING,其他同理;考虑没有找到航班的情况。
    需要注意的是,只有高铁是可阻塞的、只有活动是可变更地点的、只有高铁是不可变更时间的。

    3.2.2 局部共性特征的设计方案

    CommonPlanningEntry类实现了PlanningEntry接口中共性方法,包括了状态转换和Getter方法。

    方法 用途
    public void allocate(PlanningEntry A, String location, String timeslot, String state) 分配资源
    public void run(PlanningEntry A, String resource, String type, String seat, String age) 完成分配后,启动项目
    public void cancel(PlanningEntry A) 取消项目
    public void end(PlanningEntry A) 结束项目
    public void block(PlanningEntry A, String location_A, String timeslot_A) 阻塞项目(高铁)
    public String getName(PlanningEntry A) getter&setter
    public String getState(PlanningEntry A)

    3.2.3 面向各应用的PlanningEntry子类型设计(个性化特征的设计方案)

    3个子类型的不同主要在于两方面:Location、TimeSlot、Resource等信息的存储模式和信息的修改。以FlightPlanningEntry为例:

    我的存储用数组实现,由于Flight的location由两个,因此用[1][2]分别表示起飞地点和抵达地点;信息修改同理,根据不同计划项信息的修改特点进行设计。分配资源只需修改location、timeslot和state的具体数据

    3.3 面向复用的设计:R

    资源有多种,因为被设计为一个接口,有3个实现类:Flight、Train和Activity。接口中有3种子类的工厂方法。由于用数组实现,因此在allocated时就已经将项目的resourece输入,以flight为例,

    3.4 面向复用的设计:Location

    原本打算采用一个List来存储若干的位置,通过PlanningEntry的不同Getter来获取

    但采用数组存储后——对Activity只需将location存在[i][2],对Flight只需将出发点存在[i][4]、结束点存在[i][5],对Train只需将location存在[i][2]~[i][4]

    3.5 面向复用的设计:Timeslot

    Time Slot设计同理location,两点分别代表对应的位置的到达和离开时间。由此设计,可以精确到每个地点的到达和离开时间,可以分别适应有一个地点的活动、两个地点的航班、多个地点的高铁。
    由此,3种不同的计划项,通过不同的Getter实现不同的特征。

    3.6 面向复用的设计:EntryState及State设计模式


    采用State设计模式,把EntryStates设计成一个接口,再用几个类来实现了WAITING、ALLOCATED、RUNNING、BLOCKED、ENDED、CANCELLED几个状态。状态的实现采用静态属性和私有化构造器的办法来节约内存。
    这里使用一个SetAndGet方法实现后续设定并获得状态的功能

    3.7 面向应用的设计:Board

    Column 1 Column 2 Column 3 Column 4
    显示屏 航班 抵达屏 过去1小时~未来1小时内抵达的航班信息、状态
    出发屏 过去1小时~未来1小时内起飞的航班信息、状态
    高铁 抵达屏 过去1小时~未来1小时内抵达的高铁信息、状态(需考虑经停车次)
    出发屏 过去1小时~未来1小时内起飞的高铁信息、状态(需考虑经停车次)
    活动版 会议室预订表 当日所有活动以及状态

    实验指导书中说到,Board是直接面向应用设计的,于是我直接实现了FlightBoard、TrainBoard、CourseBoard三个类。每个Board都有time和location属性来记录这个信息板要展示的时间和地点,以Interator按时间顺序进行排序。

    ————————————————————————————————

    3.8 Board的可视化:外部API的复用

    3.9 PlanningEntryCollection的设计

    用二维数组实现,以main()选择需要实现的功能

    该ADT是PlanningEntry的集合类。
    ———————————————————————————————

    3.10 可复用API设计及Façade设计模式

    3.10.1 检测一组计划项之间是否存在位置独占冲突

    双层循环遍历。设计思路是对于传入的一组计划项,如果他们当中有位置相同&&位置不可共享&&起止时间有交集的话则是存在独占冲突的,否则没有。

    3.10.2 检测一组计划项之间是否存在资源独占冲突

    同上,条件变为资源部分是否有冲突。

    3.10.3 提取面向特定资源的前序计划项

    提取面向特定资源的前序计划项。针对某个资源 r 和使用 r 的某个计划项 e,从一组计划项中找出 e 的前序 f, f 也使用资源 r, f 的执行时间在 e 之前,且在 e 和 f 之间不存在使用资源 r 的其他计划项。若不存在这样的计划项 f,则 返回 null。 如果存在多个这样的 f,返回其中任意一个即可。
    对 ROM、学习资 料等不可区分个体的资源,该 API 不适用。

    3.11 设计模式应用

    3.11.1 Factory Method

    设置3个PlanningEntry接口的工厂方法,分别新建1种计划项子类型。以Flight Schedule为例,需要输入Location、TimeSlot和计划项编号3个参数,返回一个FlightSchedule计划项类型:

    3.11.2 Iterator

    在Board中直接返回一个List Entries的Iterator即可。
    public Iterator iterator() {
    return entries.iterator();
    }

    3.11.3 Strategy

    在PlanningEntriesAPI中直接设置抽象方法

    ————————————————————————————————

    3.12 应用设计与开发

    3.13 基于语法的数据读入

    (正则表达式)

    3.14 应对面临的新变化

    3.14.1 变化1

    对于活动、航班、高铁的一个、两个、多个位置管理,我采用数组存贮他们的位置,因此只需获取对应的下标即可查询相应位置。

    3.14.2 变化2

    高铁的变化在于,若被分配资源后则不能被取消。这个变化可以通过重写cancel()方法,增加判断语句限制前置状态即可。

    3.14.3 变化3

    学习活动与高铁和航班不同的是,学习活动的时间和地点都是可变化的,这个变化可以通过增加可阻塞的活动名单,该方法代价较小

    3.15 Git仓库结构

    4 实验进度记录

    日期 时间段 计划任务 实际完成情况
    5.9 10小时 完成底层代码 延期
    5.10 9小时 完成底层代码 完成
    5.14~5.16 20小时+ 完成客户的 完成
    5.17 2小时 完善报告 完成

    5 实验过程中遇到的困难与解决途径

    1. 正则表达式不会使用

      参与群聊、上网查阅资料

    2. 不理解多种设计模式的概念

      重看网课

    赞(0) 打赏
    未经允许不得转载:爱站程序员基地 » 2020春软件构造Lab3 Reusability and Maintainability Oriented Programming