CSDN博客传送门

@

一、架构设计

(一)第一次作业

本次作业关于UML中的类图。如果说JAVA是用来描述对象及其联系的一种建模语言,那么UML则是用来描述JAVA语言的高层次建模语言,而我们需要完成的作业则是对UML语言的描述及对UML对象的管理。随着层次(此处“层次”并非抽象层次,而是结构层次,高层和底层之间具有组合关系)逐渐地提高,思想的复杂度和抽象性也成倍地提高(需要在多个不同层次去思考问题)。

作业需求分析

  • 通过实现UmlInteraction这个官方提供的接口,来实现自己的UmlInteraction解析器。

由于对象之间的关系无非内涵(组合)、外延(继承)、耦合(联系):

  • 用缩进表示结构层次(组合关系)
  • 用括号()表示抽象层次(继承关系)
  • []表示指向对象的指针(联系关系):其中必然联系同时是对象中的组合(需要用缩进表示),偶然联系则直接写在对象后面

用对象图来表示这三种关系如下:

  • ClassModel

    • Interfaces

      • Interface(Object)

        • Associations

          • Association

            • [Object]
        • Generalizations(Generable)
          • Generalization1(Generable)

            • [Interface]
        • Implementations
          • Implementation

            • [Interface]
        • Operations
          • Operation
    • Classes
      • Class(Object)

        • Associations

          • Association

            • [Object]
        • Attributes
          • Attribute
        • Implementations
          • Implementation

            • [Interface]
        • Operations
          • Operation

            • Parameter
        • Generalization2(Generable)
          • [Class]

建立类图

由于JAVA语言对于上述对象图关系的描述非常难受,很多关键词之间发生重复而不得不重名,而且建立这样深层次的结构层次非常困难(从这个角度来说:JAVA很难说是一个优秀的面向对象语言)

粗线表示继承extends,细线表示组合contains,虚线表示联系associates



因为建立了大量的包来管理层次关系,导致用IDEA自带的diagram画出的图不忍直视,怎么调都不能画出期望的那样。一直是一堆点都点不开的包名:

bug修复

几乎所有的bug都出现在对于异常输出上:We expected "No, attribute mData in NetworkParam, mGrad in NetworkParam, are not hidden." but we got "No, attribute mData in Float32NetworkParam, mGrad in Float32NetworkParam, are not hidden." at line 18

在改过基本的问题后,出现了一种特殊的情况,而这种情况恰恰是指导书上几乎没有提示的部分:

在调查C3的Attribute1的Visibility时,确实是重复了,但他的父类已经犯了这个错误,应该先扔出父类的异常。

在这里,检查异常应该有一个明晰的先后关系:而且结构层次越浅,抽象层次越高的对象的异常应该最先被检查出来,抛出之后应该直接拒绝执行下一步。

(二)第二次作业

作业需求分析

本次作业,在上次作业基础上,扩展解析器,使得能够支持对UML顺序图和UML状态图的解析,并能够支持几个基本规则的验证:

对象图在第一次基础上,增加了statechartmodel collaborationmodel两个新模型,而且这两个模型几乎和之前的classmodel没有任何关系,甚至可以看做两个新工程:

  • statechartmodel

    • StateChartSet

      • StateChart{=StateMachine}

        • Region

          • Transition{含有Event}
          • State
  • collaborationmodel
    • Collaboration{=InteractionSet}

      • Interaction

        • Lifeline
        • Message

建立类图





如图所示,建立的类图仅表示类的名称、对象关系,就已经相当复杂:30个类,分散在8个包中。结构层次一目了然,但是由于JAVA语言的局限性,仍然没有按照对象图所示建立类。

checkForUml002实现方式

如类图,checkForUml002由于只与类有关,交由ClassSet处理,依次遍历所有类MyClass,而MyClass中设有以下函数:对三种情况进行了区分,并依次添加。

public HashSet<? extends AttributeClassInformation> checkForUml002() {
HashSet<AttributeClassInformation> set = new HashSet<>();
//1. 来自重复的<属性,属性>
for (Map.Entry<String, UmlAttribute> entry :attributes.getMap().entrySet()) {
if (entry.getValue() == null) {
set.add(new AttributeClassInformation(entry.getKey(), getName()));
}
}
//2. 来自重复的<属性,对端>
for (UmlAssociationEnd end : getAssociations().getList()) {
if (attributes.contains(end.getName())) {
set.add(new AttributeClassInformation(end.getName(), getName()));
}
}
//3. 来自重复的<对端,对端>,注意null不算
HashSet<String> endSet = new HashSet<>();
for (UmlAssociationEnd end : getAssociations().getList()) {
if (end.getName() != null && endSet.contains(end.getName())) {
set.add(new AttributeClassInformation(end.getName(), getName()));
} else {
endSet.add(end.getName());
}
}
return set;
}

checkForUml008/009实现方式

这两个check是一起完成的,实现方式非常巧妙:在每个MyObject包含的Generable中设置了一个HashMap:private HashMap<UmlClassOrInterface, Boolean> map = null;

模型结束后自动将父类加到这个map中去,如果map已经含有这个父类了,将value值置为true

并且用到了深度优先递归,先添加正在查找的对象,如果它没有更新map,则等它更新完毕再继续。最后对于MyObject中的check都能一步完成:

public boolean checkForUml008() {
return getGenerable().getMap().containsKey(IdManager.getById(id));
} public boolean checkForUml009() {
return getGenerable().getMap().containsValue(true);
}

StateChart.getSubsequentStateCount实现方式

相当于找到有向图中某个对象的所有可达点。但是最好是在模型结束时将所有点的可达点都找到。个人用的算法是对每个节点都用一次Bfs,将所有到达的节点都记录在表内。(可能有复杂度更低的算法)

private HashMap<String, HashSet<String>> map;
//<状态的name,后续状态名称集合>,null表示该状态duplicate
//如果是起始和终止态,忽略不计
private void Bfs(String name) {
HashSet<String> arrived = map.get(name);
HashSet<String> nextSet = new HashSet<>(arrived);
while (!nextSet.isEmpty()) {
String fromNode = nextSet.iterator().next();
nextSet.remove(fromNode);
if (map.get(fromNode) == null) {
continue;
}
for (String toNode : map.get(fromNode)) {
if (!arrived.contains(toNode)) {
nextSet.add(toNode);
arrived.add(toNode);
}
}
}
}

二、四个单元中架构设计及OO方法理解的演进

四个单元依次是表达式求导 多线程电梯 JML规格化 UML模型化,四次的角度各有不同,但视角逐渐变得全面,变得有层次、有深度。尤其是最后一次竟然直接以JAVA语言本身为对象进行语言上的思考与设计。

OO对我的最大影响并不是一个个具体的算法(尤其是图论中的Bfs,Floyd,Dijstra,Dfs);不是一些具体的数据结构(尤其是容器类的使用HashMap,HashSet,Arraylist,LinkList);不是一些具体的多线程交互模式(如生产者——消费者模式、工厂模式、订阅——发布者模式);不是一些具体的设计模式(如单例模式、守护者模式、观察者模式);不是一些具体的设计原则(尤其是SOLID原则:SRP,OCP,LSP,ISP,DIP);却是面向对象在哲学视角的思想与方法论

此篇博文详细讨论了面向对象的哲学视角与方法论。

三、四个单元中测试理解与实践的演进

测试依次接触到:自动化测试、规格化测试、单元测试

自动化测试:用代码将数据管理好,并自动去运行整个程序,将数据导入并进行对比的方式。

规格化测试:针对方法而言,对每个方法都独立地写一个LLR(Low Level Request,即规格),让相应软件自动生成数据进行验证。

单元测试:针对方法而言,是一种内部的样例,直接对类进行初始化,调用相应函数,检验结果。

应用异常代价:软件都是为了某一个应用而实现的,在软件工程真正运行过程中大量的从用户端传来的数据可能会导致工程出现漏洞,有时甚至会出现极大的经济上的损失。这样的测试也是有代价的,更多时候要权衡测试的成本和应用异常代价。

个人认为,写一个单元测试时非常费力的,写了半天只检验了一个函数,而且还不能保证100%正确;写一个LLR(规格化测试)也是非常费力的,而且从LLR到实现也是吃力不讨好的过程,不如直接用自然语言描述的需求更好实现。虽然有所谓的代码覆盖率、分支覆盖率层次上的检验,其时间和空间代价对于一般的应用程序都是不可接受的。只有航天航空那种要求非常严格的软件工程才会有这样严苛的要求。

最后剩下的就是自动化测试了,可以说这个是检查代码功能正确性,已经代码效率最佳的方法。首先将所有测试样例放在同一个文件目录下,可以用python语言import OS,用命令行调用自动生成JAVA可运行程序,依次再运行所有样例,与结果进行比较。这样的自动化测试就相当于评测机了。说到底,这个才是最为实用的测试方式。

四、三个具体改进建议

  1. 对优秀代码进行全面而有层次地解读,学习大佬的思想
  2. 与其他学科进行交叉解读,如面向对象在哲学视角的思考,在计算机网络层面的关联
  3. 作业更加贴合实际一些、具体一些,如写一些关于UI方面的,写游戏这样能提起同学兴趣,并对同学有些实际的作用

OO_Unit4_UML模型化设计的更多相关文章

  1. OO_Unit4 UML模型化设计总结

    OO_Unit4 UML模型化设计总结 任务简介:本单元在介绍了UML中几种基本的模型图元素的基础上,通过实现课程组提供的官方接口来完成自己的UML解析器. 架构设计 本单元最终的整体架构图如下(不包 ...

  2. .NET领域驱动设计—实践(穿过迷雾走向光明)

    阅读目录 开篇介绍 1.1示例介绍 (OnlineExamination在线考试系统介绍) 1.2分析.建模 (对真实业务进行分析.模型化) 1.2.1 用例分析 (提取系统的所有功能需求) 1.3系 ...

  3. .NET领域驱动设计—初尝(三:穿过迷雾走向光明)

    开篇介绍 在开始这篇富有某种奇妙感觉的文章之旅时我们先短暂的讨论一下关于软件开发方法论的简要: 纵观软件开发方法论,从瀑布模型.螺旋模型.RUP(统一软件开发过程).XP(极限编程).Agile(敏捷 ...

  4. [转] .NET领域驱动设计—实践(穿过迷雾走向光明)

    阅读目录 开篇介绍 1.1示例介绍 (OnlineExamination在线考试系统介绍) 1.2分析.建模 (对真实业务进行分析.模型化) 1.2.1 用例分析 (提取系统的所有功能需求) 1.3系 ...

  5. 五指CMS发布1.4版本,更多的新功能

    五指cms v1.4变更: 新增内容手动分页新增百度地图新增订单管理模块新增订单地址管理增加Microsoft YaHei字体新增推广邀请模块新增私密下载,下载函数 新增百度地图新增筛选功能 修正全局 ...

  6. 五指CMS发布,主打高性能

    近日,五指CMS正式发布.给沉静已久的国内 CMS 行业引来不少的关注.五指CMS由原PHPCMS v9的负责人王参加主导开发.我们可以看到,由于移动互联网以及大数据的崛起,个人站长市场的逐渐减少,国 ...

  7. 五指CMS v1.2 GBK 发布下载

    五指CMS v1.2 GBK 版本下载地址: http://www.wuzhicms.com/uploadfile/wuzhicms/wuzhicms-v1.2.zip       从内测到公测,五指 ...

  8. 面向对象程序设计第四单元总结(UML系列)

    2019面向对象程序设计第四单元总结 前言 ​ 本单元是面向对象程序设计课程的最后一个单元了,本单元是和UML模型相关,也就是说,我们需要正确理解UML模型的基础上,对构建出的UML模型进行解析,但是 ...

  9. BUAA_OO_2020_Unit4_总结博客

    BUAA_OO_2020_Unit4_总结 2020年春季学期第十六周,OO第四单元即最终章落下帷幕,本单元是利用Java进行UML类图的解析,完成对类图.顺序图.状态图的内部查询操作与简单的规则判断 ...

随机推荐

  1. vue 给一个值重置初始值

    查了下资料很多都是如下: 1. this.$options.data() 这个可以获取原始的data值,this.$data 获取当前状态下的data,拷贝重新赋值一下就行了. 1 Object.as ...

  2. 2019_西湖论剑_预选赛 testre

    2019_西湖论剑_预选赛 testre 程序中关键操作是比较ptr,其中夹杂的一部分v26计算是为了混淆我们的分析.那么我们只要跟踪ptr数组的生成便可,向上发现v11,加密操作数组. 接下来跟踪v ...

  3. WPF 反射加载Geometry几何图形数据图标

    相信大家在阅读WPF相关GitHub开源项目源码时都会看见一串串这种数据 这种Geometry数据就是几何图形数据 为什么要用Geometry数据做图标? 有一种做法是使用ttf字体文件代替,不过使用 ...

  4. Edge 浏览器开发工具新增了 3D 视图,你尝试了吗?

    在使用开发者工具的时候,无意间发现了一个3D面板,如下: 仔细想想,这应该是之前 Firefox 的特性啊,不过后来去掉了,说是太难维护,没想到 Edge 也添加了这个特性. 使用该特性,你可以完成如 ...

  5. Android Studio 之 RadioButton

    •任务 如何通过 RadioButton 实现如图所示的界面? •基本用法 RadioButton 单选按钮,就是只能够选中一个,所以我们需要把 RadioButton 放到 RadioGroup 按 ...

  6. Python脚本打包成exe执行文件

    需求 一个教辅目录结构检查工具,目录结构是[书籍]-[章节]-[题目|答案]-[*.jpg],后台有个异步处理的服务,需要强依赖这个目录结构. 书籍解析是单独的pipeline,日志对用户不可见,这里 ...

  7. Typora标题自动编号+设定快捷键技巧

    Typora标题自动编号 提示:要了解将这些CSS片段放在哪里,请参阅添加自定义CSS. 打开Typora偏好设置,打开主题文件夹,在主题文件夹中创建base.user.css文件,放置以下内容,则T ...

  8. 让你的程序炫起来!少有人知道但超酷的 Python 进度条开源库

    本文适合有 Python 基础的朋友 本文作者:HelloGitHub-Anthony HelloGitHub 推出的<讲解开源项目>系列,本期介绍让你快速拥有完美进度条的 Python ...

  9. java面试-谈谈你对volatile的理解

    一.volatile特性: volatile是Java虚拟机提供的轻量级的同步机制.主要有三大特性: 保证可见性 不保证原子性 禁止指令重排序 1.保证可见性 1)代码演示 AAA线程修改变量numb ...

  10. SparkStreaming使用mapWithState时,设置timeout()无法生效问题解决方案

    前言 当我在测试SparkStreaming的状态操作mapWithState算子时,当我们设置timeout(3s)的时候,3s过后数据还是不会过期,不对此key进行操作,等到30s左右才会清除过期 ...