北航oo作业第三单元小结
一、梳理JML语言的理论基础
1、jml的注释结构
jml注释语言的每一行都以@作为开始,若是块注释,则需要在注释块的首尾使用/*@ 与@*/
2、jml的表达式体系
1、原子表达式
表达式可以看作是一个原子类型,常见的有\result表达式(用于表达某个方法执行后的结果)、\old表达式(用来表示某个对象执行某操作之前的值)。
2、量化表达式
量化表达式是对给定范围内对象批量操作的表达式,其存在大大简化了jml语言,常见的有\forall表达式(范围内对象,都要满足某要求)、\exists表达式(范围内存在对象,满足某要求)、以及\sum表达式、\product表达式、\max表达式等数学方法的量化表达式
3、集合表达式
用来在jml规格中构造一个集合(容器),来简化jml规格
4、操作符
包括算数操作符和逻辑操作符。例如等价操作符<==> 与 ==,其中特别要注意的是<==> 与 ==这样的操作符,优先级是不一样的!
此外操作符还包括变量引用操作符,例如\nothing指示一个空,\everything指示一个全集。
3、jml的方法规格
我们使用与学习的方法规格只是最基础的部分,核心内容是三方面:前置条件、后置条件、副作用限定。
1、前置条件
前置条件使用requires语句来表示,requires P意味着需要确保P的值为真。需要注意的是,requires语句如果多行一起出现,是并列条件,需要全部满足。
2、后置条件
后置条件使用ensures语句来表示,ensures P意味着需要确保P的值为真。同样,ensures语句如果多行一起出现,是并列条件,需要全部满足。
3、副作用限定
在方法执行时,为了满足前置条件与后置条件,我们可能会对对象做一些与前置条件和后置条件无关的改动,也就是副作用。有时候需要通过副作用限定来对方法实现进行约束。
这里,我们可以选择assignble和modifiable。
assignble 表示可赋值,而 modifiable 则表示可修改。虽然二者有细微的差异,在大部分情况 下,二者可交换使用。
这两个关键词既可以约束特定的对象,表示更改特定对象。也可以选择约束\nothing 和 \everything这样的关键词,来表示什么都不更改,或是全部更改。
4、其他
当前置条件与后置条件需要对多个对象进行约束时,可以与用\forall或者\exists表达式结合使用。
我们使用signals语句,来表示异常处理,语句signals (***Exception e) b_expr 的意思是当 b_expr 为 true 时,方法会抛出括号中给出 的相应异常e。
4、jml的类型规格
不变式(invariant),语法上定义 invariant P ,其中 invariant 为关 键词, P 为谓词,表示要求在所有可见状态下都必须满足的特性。
状态变化约束(constraint),用来对前序可见状态和当前可见状态的 关系进行约束。
5、总结
jml语言是一套逻辑严密的注释语言体系,通过对方法行为的描述,预防bug的出现,并使得检查过程比原先轻松,提高了代码的可维护性。
二、jml应用工具链情况
首先,是jml语言的编写,可以使用专门的jml编译器。
jml规格的校验,可以使用openjml。
JMLUnitNG可以根据规格的实现自动生成TestNG测试样例。
三、部署JMLUnitNG
1、测试代码
package demo;
public class Demo {
private /*@ spec_public @*/ int[] nodeList; public Demo(int[] nodeList) {
this.nodeList = new int[16];
} /*@ requires index >= 0 && index < size();
@ assignable \nothing;
@ ensures \result == nodes[index];
@*/
public /*@pure@*/ int getNode(int index){
if (index >= 0 && index < size()) {
return nodeList[index];
} else {
return 0;
}
} //@ ensures \result == (nodes.length >= 2);
public /*@pure@*/ boolean isValid(){
boolean ret = false;
if (nodeList.length >= 2) {
ret = true;
}
return ret;
} public static void main(String[] args){ } }
2、测试方法
首先,尽管已经有很多前人感谢过伦佬了,但我还是要在这里郑重地再感谢一次伦佬。
3、测试结果
[TestNG] Running:
Command line suite
Passed: racEnabled()
Passed: constructor Demo()
Passed: <<demo.Demo@1a8f2434>>.getNode(-2147483648)
Passed: <<demo.Demo@5f5a92bb>>.getNode(0)
Passed: <<demo.Demo@376b9c22>>.getNode(2147483647)
Passed: <<demo.Demo@54768a01>>.isValid()
Passed: static main(null)
Passed: static main({})
===============================================
Command line suite
Total tests run: 8, Failures: 0, Skips: 0
===============================================
4、测试思考
这个自动化测试emmmm,实际上,只是测试了几个边界条件,似乎正能起到一个锦上添花的作用。
四、架构设计
1、第一次作业
在pathcontainer中,我的选择是构造三个hashmap,一个用path作为key,pathid作为value。另一个用pathid作为key,path作为value。(这里需要在mypath类中重构path对象的hashcode方法)。这两个hashmap实现了path的快速查找和改动(总有一个hashmap可以用key查找,查找出来的value作为另一个hashmap的key)。第三个hashmap,使用node作为key,node的数目作为value,用来,存储当前容器内的节点数量。
在path中,除了本身的节点数组外,我还构造了一个hashmap,用于判断path中是否含有某node。
2、第二次作业
本次作业要求,在第一次作业的基础上,加入了判断两个节点是否联通,两个点是否能构成一条边,以及得到两个节点间的最短路径。
我并没有对第一次的构造进行改动,而是在第一次作业的基础上又构造了两个静态数组,一个hashmap,和一个arraylist,其中hashmap是保存节点与映射节点的关系(我将图内的节点映射到了0到nodesize内),具体做法是,先检查arraylist如果arraylist不为空,从arraylist内取出一个可映射的值,与当前节点映射。否则,当前映射id与当前节点映射并加一。当一个节点,不存在图中时,将其从hashmap中删除,并将对应的映射值,存入arraylist中。
两个静态数组都是大小为nodesize的二维数组,(节点查找使用映射值)一个存储的是当前图内的点的联通情况(权重为1),另一个存储的是对联通性矩阵进行floyd运算后的矩阵。
3、第三次作业
本次作业,对nodesize要求更改,并且添加了新的需求,联通块数量计算,最少票价计算,最少换乘次数计算,最少不满意度计算。
首先,nodesize的更改,由于我没有使用magic number(上一次作业的教训),直接改动nodesize即可。
此外,分析发现,新的需求中,联通块计算可以通过并查集实现,我增加了并查集方面的方法。
而剩下的三个需求,其实可以和第二次作业中的最短路径一起归纳为图的权重问题。我对第二次作业的floyd方法进行了重构,重构成了一个templatefloyd(c++课中的模板类思想),并又构建了5个二维矩阵,用来存储不同需求下的图的权重矩阵和floyd运算后的结果矩阵。
五、bug与修复
1、第一次作业
未发现bug。
2、第二次作业
本次作业中,我忽略了得到最短路径方法的jml规格中的描述:当fromnodeid == tonodeid时,最短路径为0 ,导致了大面积的wa。
3、第三次作业
未发现bug。
六、心得体会
首先,我深刻理解了这一单元最开始时,老师在课上反复强调的,只要严格按照jml来实现,就不会有bug。自己的bug也是没有完全按照jml的约束实现。
然而,在jml的实现中,仅仅做到实现jml也是不足够的。我的第三次作业的强测有一个点过的特别危险,35s的时间limit,我花了34.6779s跑完了程序。诚然,我严格按照jml约束实现了,但我没有考虑到性能的优化。在jml的实现中,还要注意性能的优化。
北航oo作业第三单元小结的更多相关文章
- 北航oo作业第四单元小结
1.总结本单元两次作业的架构设计 在我动手开始总结我的设计之前,我看了其他同学已经提交在班级群里的博客,不禁汗颜,我是真的偷懒.其他同学大多使用了新建一个类,用以储存每一个UMLelemet元素的具体 ...
- 北航OO(2020)第三单元博客作业
一.JML理论基础及相关工具链 1.JML理论基础 该部分梳理本单元作业中涉及到的JML知识. 1.1注释结构 JML采用javadoc注释的方式来表示规格,且每行以@开头.通过使用//@annota ...
- OO作业第三单元总结
目录 一.JML语言理论基础及应用工具链 二.部署JMLUnitNG,自动生成测试用例 三.架构设计 第一次作业 第二次作业 第三次作业 四.Bug分析 五.心得体会 一.JML语言理论基础及应用工具 ...
- 北航oo作业第一单元小结
前言 在经过了三次艰辛的oo作业后,oo课程的第一单元告一段落,这一单元,我作为一个oo小白,开始了解oo的编程思想,也有了自己的一点心得体会.把笔粗成字,不当之处,还请各位大佬多多指教. 一.分析程 ...
- BUAA OO 2019 第三单元作业总结
目录 总 JML规格化设计 理论基础 工具链 规格验证 验证代码 代码静态检查 自动生成测试样例 生成结果 错误分析 作业设计 第九次作业 架构 代码实现 第十次作业 架构 代码实现 第十一次作业 架 ...
- 北航OO(2020)第四单元博客作业暨学期总结
一.第四单元架构设计 1.第一次作业 我在本次作业中设置了多个储存结构:Directory,ElementsInName,ElementsInId,Cache. Directory: 顾名思义,这是个 ...
- OO第三单元小结
目录 JML理论基础 JML工具链 openjml使用 openjml总结 jmlunitng使用 代码分析 第一次作业 第二次作业 第三次作业 测试&bug分析 黑盒测试 白盒测试(Juni ...
- OO第三次博客作业--第三单元总结
一.JML 语言的理论基础及应用工具链 JML 是一种行为接口规格语言,提供了对方法和类型的规格定义手段.通过 JML 和其支持工具,不仅可以基于规格自动构造测试用例,并整合了 SMT Solver ...
- OO课第三单元总结
一.梳理JML语言的理论基础 (1)理论基础 JMl的出现很大程度上一为了行为接口的规范化,用这种语言来指定特定模块的特定功能.JML的核心部分分为三个部分:前置条件(requires).后置条件(e ...
随机推荐
- Ajax的包装
/** * Created by Administrator on 2016/12/27. *//** * 创建XMLHttpRequest对象 * @param _method 请求方式: post ...
- 相关符号标点的英文(IOS学习)
尖括号: angle bracket 方括号: square bracket 花括号: curly brace 圆括号: parentheses 逗号: comma 冒号: colon 逗号: sem ...
- 阶段3-团队合作\项目-网络安全传输系统\sprint3-账号管理子系统设计\第2课-账号管理子系统设计
账号管理子系统的设计 客户端需要登录到服务器,在服务器去查询数据库,进行验证该用户. 打开client.c文件 编译之 把它复制到开发板里面去 这个程序是在本地数据库测试的!!!!!!!!!!!!!! ...
- Struts2学习第七课 result
result 是action节点的子节点 result 代表action方法执行后,可能去的一个目的地 一个action节点可以配置多个result子节点. result的name属性值对应着acti ...
- 微信小程序自学第三课:文件作用域,模块化
一.文件作用域 在 JavaScript 文件中声明的变量和函数只在该文件中有效:不同的文件中可以声明相同名字的变量和函数,不会互相影响. 通过全局函数 getApp() 可以获取全局的应用实例,如果 ...
- Vue中使用jquery
在vue项目中,需要实现某些特定的功能时,使用mvvm模式不易实现.因此引入jquery包来完成需求 npm install jqueryimport $ from jquery //在需要使用的页面 ...
- windows severs 2008r2 180天激活
无需破解:Windows Server 2008 R2 至少免费使用 900天 1.首先安装后,有一个180天的试用期. 2.在180天试用期即将结束时,使用下面的评估序列号激活Svr 2008 R2 ...
- Tomcat服务器介绍及配置
一.Tomcat简介 Tomcat(Apache)是当前应用最广的JavaWeb服务器 1.Tomcat版本: 安装版:需要安装,一般不考虑使用.一个电脑只能安装一个,卸载也比较麻烦! 解压版: 直接 ...
- 我的省选 Day -12
Day -12 今天是三月份的最后一天,春天真的也就走过了1/3了呢. 昨晚做了个神秘而悲伤的梦.(这样子写下来会不会不太好.. 我梦见欢洛了. 那是在新校区的门口,我看见他,然后向他跑过去,他转身对 ...
- Flutter SDK的下载与安装步骤 (mac版)
本月初(应该是2018年12月4日),Google在其Flutter Live 2018大会上正式发布 Flutter 1.0 版本. 当然我们不会怀疑Google团队的技术实力,但它和React N ...