实验要求

  • 初步掌握单元测试和TDD
  • 理解并掌握面向对象三要素:封装、继承、多态
  • 初步掌握UML建模
  • 熟悉S.O.L.I.D原则
  • 了解设计模式

实验内容

  • 单元测试
  • 面向对象三要素
  • 设计模式初步
  • 练习

实验步骤(实现四则运算,并进行测试)

单元测试

  1. 伪代码:以简洁的自然语言表明设计步骤;
百分制转五分制:
如果成绩小于60,转成“不及格”
如果成绩在60与70之间,转成“及格”
如果成绩在70与80之间,转成“中等”
如果成绩在80与90之间,转成“良好”
如果成绩在90与100之间,转成“优秀”
其他,转成“错误”
  1. 产品代码:用以实现特定功能的程序或机器语言;
package exp1;
public class MyUtil{
public static String percentage2fivegrade(int grade){
//如果成绩小于60,转成“不及格”
if (grade < 60)
return "不及格";
//如果成绩在60与70之间,转成“及格”
else if (grade < 70)
return "及格";
//如果成绩在70与80之间,转成“中等”
else if (grade < 80)
return "中等";
//如果成绩在80与90之间,转成“良好”
else if (grade < 90)
return "良好";
//如果成绩在90与100之间,转成“优秀”
else if (grade < 100)
return "优秀";
//其他,转成“错误”
else
return "错误";
}
}
  1. 测试代码:用以对产品代码进行测试的代码;
package lab02;

import org.junit.Test;

import static org.junit.Assert.*;
public class MyUtilTest { @Test
public void testPercentage2fivegrade() throws Exception {
assertEquals("不及格",MyUtil.percentage2fivegrade(56));
assertEquals("及格",MyUtil.percentage2fivegrade(66));
assertEquals("中等",MyUtil.percentage2fivegrade(76));
assertEquals("良好",MyUtil.percentage2fivegrade(86));
assertEquals("优秀",MyUtil.percentage2fivegrade(96));
}
}

运行结果如下:

TDD(Test Driven Devlopment, 测试驱动开发)

  • TDD:先写测试代码,然后再写产品代码的开发方法。
  • TDD的一般步骤如下:
  1. 明确当前要完成的功能,记录成一个测试列表
  2. 快速完成编写针对此功能的测试用例
  3. 测试代码编译不通过(没产品代码呢)
  4. 编写产品代码
  5. 测试通过
  6. 对代码进行重构,并保证测试通过(重构下次实验练习)
  7. 循环完成所有功能的开发
  • TDD的编码流程:

    1. 增加测试代码,JUnit出现红色段码
    2. 修改产品代码
    3. 实现
  • IDEA环境:鼠标右键->Go To ->Test



面向对象三要素

  • 抽象

    即“取其精华去其糟粕”的过程。将若干事物中相同的部分进行剥离整理,并形成具有某特定功能的产品,这一过程即为抽象。

    过程抽象的结果是函数,数据抽象的结果是抽象数据类型其显而易见的好处是(在程序设计中)减少了代码大重复性,提高了效率。
  • 封装、继承与多态
  1. 面向对象(Object-Oriented)的三要素包括:封装、继承、多态。面向对象的思想涉及到软件开发的各个方面,如面向对象分析(OOA)、面向对象设计(OOD)、面向对象编程实现(OOP)。OOA根据抽象关键的问题域来分解系统,关注是什么(what)。OOD是一种提供符号设计系统的面向对象的实现过程,用非常接近问题域术语的方法把系统构造成“现实世界”的对象,关注怎么做(how),通过模型来实现功能规范。OOP则在设计的基础上用编程语言(如Java)编码。贯穿OOA、OOD和OOP的主线正是抽象。
  2. 封装:将数据与相关行为包装在一起以实现信息就隐藏。封装实际上使用方法(method)将类的数据隐藏起来,控制用户对类的修改和访问数据的程度,从而带来模块化(Modularity)和信息隐藏(Information hiding)的好处;接口(interface)是封装的准确描述手段。 Dog类通过使用类和访问控制(private,public)隐藏了属性color,开放了接口setColor(),getColor(),bark()和toString。
  3. 继承:以封装为基础,一个类的定义可以基于另外一个已经存在的类,即子类基于父类,从而实现父类代码的重用。其更为广泛而重要的作用是实现多态。
  • 例子:

封装

public class Dog {
private String color;
public String getColor() {
return color;
}
public void setColor(String color) {
this.color = color;
}
public String bark(){
return "汪汪";
}
public String toString(){
return "The Dog's color is " + this.getColor() +", and it shouts "+ this.bark() + "!";
}
}

检测

public class DogTest {
public static void main(String[] args) {
Dog d = new Dog();
d.setColor("Yellow");
getInfo(d);
}
public static void getInfo(Dog d) {
System.out.println(d.toString());
}
}

设计模式

  • S.O.L.I.D原则
  1. SRP(Single Responsibility Principle,单一职责原则)

    对象提供单一职责的高度封装,对象的改变仅仅依赖于单一职责的改变
  2. OCP(Open-Closed Principle,开放-封闭原则)

    即对扩充开放(功能可增加),对修改封闭(源代码不可改动)

    OCP实现手段:(1)抽象和继承,(2)面向接口编程
  3. LSP(Liskov Substitusion Principle,Liskov替换原则)

    子类必须可以被其基类所代,父类型对象可以被子类型对象所取代
  4. ISP(Interface Segregation Principle,接口分离原则)

    客户不应该依赖他们并未使用的接口
  5. DIP(Dependency Inversion Principle,依赖倒置原则)
  • 模式与设计模式

    模式是某外在环境(Context) 下﹐对特定问题(Problem)的惯用解决之道。其中最重要的是设计模式。
  • 设计模式实示例

    设计模式四个基本元素

    Pattern name:描述模式,便于交流,存档

    Problem:描述何处应用该模式

    Solution:描述一个设计的组成元素,不针对特例

    Consequence:应用该模式的结果和权衡

练习

使用TDD的方式设计关实现复数类Complex

伪代码

1)复数类ComplexNumber的属性
  realPart: 实部,代表复数的实数部分
  imaginPart: 虚部,代表复数的虚数部分
2)复数类ComplexNumber的方法
  ComplexNumber() 构造函数,将实部,虚部都置为0
  ComplexNumber(double realPart, double imaginPart) 构造函数,创建复数对象的同时完成复数的实部,虚部的初始化
  getRealPart() 获取实部
  getImaginaryPart() 获取虚部
  getRealPart(double realPart) 设置实部
  getImaginaryPart(double imaginPart) 设置虚部
  ComplexAdd(ComplexNumber c)  复数相加
  ComplexAdd(double realPart2)  复数相加
  ComplexMinus(ComplexNumber c)  复数相减
  ComplexMinus(double realPart2) 复数相减
  ComplexMulti(ComplexNumber c)  复数相乘
  ComplexMulti(double realPart2) 复数相乘
  toString() 把当前复数对象的实部,虚部组合成a+bi的字符串形式
  • 测试代码
package lab02;

import static junit.framework.Assert.*;
import junit.framework.TestCase;
import org.junit.Test; public class ComplexNumberTest extends TestCase {
ComplexNumber c1 = new ComplexNumber(3,5);
ComplexNumber c2 = new ComplexNumber(3,5);
double a = 5;
@Test
public void testAdd1() throws Exception {
c1.ComplexAdd(c2);
assertEquals(6.0, c1.getRealPart());
assertEquals(10.0, c1.getImaginPart());
}
@Test
public void testAdd2() throws Exception {
c1.ComplexAdd(a);
assertEquals(8.0, c1.getRealPart());
assertEquals(5.0, c1.getImaginPart());
}
@Test
public void testMinus1() throws Exception {
c1.ComplexMinus(c2);
assertEquals(0.0, c1.getRealPart());
assertEquals(0.0, c1.getImaginPart());
}
public void testMinus2() throws Exception {
c1.ComplexMinus(a);
assertEquals(-2.0, c1.getRealPart());
assertEquals(5.0, c1.getImaginPart());
}
@Test
public void testMulti1() throws Exception {
c1.ComplexMulti(c2);
assertEquals(9.0, c1.getRealPart());
assertEquals(25.0, c1.getImaginPart());
}
public void testMulti2() throws Exception {
c1.ComplexMulti(a);
assertEquals(15.0, c1.getRealPart());
assertEquals(5.0, c1.getImaginPart());
}
}
  • 产品代码
package lab02;

public class ComplexNumber {
private double realPart;
private double imaginPart;
public ComplexNumber(){
double realPart;
double imaginPart;
}
public ComplexNumber(double r, double i){
double realPart;
double imaginPart;
this.realPart = r;
this.imaginPart = i;
}
public double getRealPart(){
return realPart;
}
public double getImaginPart(){
return imaginPart;
}
public void setRealPart(double d){
this.realPart = d;
}
public void setImaginPart(double d){
this.imaginPart = d;
}
public void ComplexAdd(ComplexNumber c){
this.realPart += c.realPart;
this.imaginPart += c.imaginPart;
}
public void ComplexAdd(double c){
this.realPart += c;
}
public void ComplexMinus(ComplexNumber c){
this.realPart -= c.realPart;
this.imaginPart -= c.imaginPart;
}
public void ComplexMinus(double c){
this.realPart -= c;
}
public void ComplexMulti(ComplexNumber c){
this.realPart *= c.realPart;
this.imaginPart *= c.imaginPart;
}
public void ComplexMulti(double c){
this.realPart *= c;
}
@Override
public String toString(){
return String.format("%f + %fi", this.getRealPart(),this.getImaginPart());
}
}

UML建模

  • 利用StarUML软件进行UML建模,可以将以上思路进行具象化表示

    显示如下,很清楚地展现了每个类的成员变量、方法函数:

需求分析

  1. 在代码一的基础上,实现模块的划分;
  2. 对一些常见用例进行测试。

分析总结与实验体会(感悟、思考等)

  • 其实还是觉得比较有意思,虽然很多东西最开始不会,但我感到很新鲜,有学习的动力!

  • 了Junit单元测试,从表面上看,每个单元程序都编写测试代码似乎是增加了工作量,但是其实这些代码不仅为你织起了一张保护网,而且还可以帮助你快速定位错误从而使你大大减少修复BUG的时间。

  • 再也不用每次通过printf来判断哪里出错了,感觉逼格瞬间提升了。

  • PSP(Personal Software Process)时间:

步骤 耗时 百分比
需求分析 10min 5%
设计 10min 5%
代码实现 60min 32%
测试 75min 40%
分析总结 30min 16%

参考资料

20145211 《Java程序设计》实验报告二:Java面向对象程序设计的更多相关文章

  1. Python程序设计实验报告二:顺序结构程序设计(验证性实验)

      安徽工程大学 Python程序设计 实验报告 班级   物流191   姓名  崔攀  学号3190505136 成绩 日期     2020.3.22     指导老师       修宇 [实验 ...

  2. 20145312《Java第一次实验报告》

    20145312<Java第一次实验报告> Java开发环境的熟悉(Windows+Idea) 一.实验内容 使用Idea编辑.编译.运行.调试Java程序. 使用JDK编译.运行简单的J ...

  3. 20145213《Java程序设计》实验二Java面向对象程序设计实验报告

    20145213<Java程序设计>实验二Java面向对象程序设计实验报告 实验内容 初步掌握单元测试和TDD 理解并掌握面向对象三要素:封装,继承,多态 初步掌握UML建模 熟悉S.O. ...

  4. 20145206《Java程序设计》实验二Java面向对象程序设计实验报告

    20145206<Java程序设计>实验二Java面向对象程序设计实验报告 实验内容 初步掌握单元测试和TDD 理解并掌握面向对象三要素:封装.继承.多态 初步掌握UML建模 熟悉S.O. ...

  5. 20145308刘昊阳 《Java程序设计》实验二 Java面向对象程序设计 实验报告

    20145308刘昊阳 <Java程序设计>实验二 Java面向对象程序设计 实验报告 实验名称 Java面向对象程序设计 实验内容 初步掌握单元测试和TDD 理解并掌握面相对象三要素:封 ...

  6. 20145221 《Java程序设计》实验报告二:Java面向对象程序设计

    20145221 <Java程序设计>实验报告二:Java面向对象程序设计 实验要求 初步掌握单元测试和TDD 理解并掌握面向对象三要素:封装.继承.多态 初步掌握UML建模 熟悉S.O. ...

  7. Java实验报告二:Java面向对象程序设计

    Java实验报告二:Java面向对象程序设计                                                                               ...

  8. 实验二Java面向对象程序设计实验报告(2)

    实验二 Java面向对象程序设计 实验概述: 课程:程序设计与数据结构 班级:1623班 姓名: 邢天岳 学号:2309 指导老师:娄老师 王老师 实验日期:2017.4.16 实验名称: Java面 ...

  9. 20175212童皓桢 Java实验二-面向对象程序设计实验报告

    20175212童皓桢 Java实验二-面向对象程序设计实验报告 实验内容 初步掌握单元测试和TDD 理解并掌握面向对象三要素:封装.继承.多态 初步掌握UML建模 熟悉S.O.L.I.D原则 了解设 ...

  10. 20175316 盛茂淞 2018-2019-2 《Java程序设计》实验二 面向对象程序设计 实验报告

    20175316 盛茂淞 2018-2019-2 <Java程序设计>实验二 面向对象程序设计 实验报告 (一)单元测试 在 IDEA中我们把产品代码放在src目录中,把测试代码放在tes ...

随机推荐

  1. android 蓝牙设备监听广播

    蓝牙权限 <uses-permission android:name="android.permission.BLUETOOTH" /> 1.监听手机本身蓝牙状态的广播 ...

  2. BZOJ3743 : [Coci2014]Kamp

    d[x][0]表示x点向下走且回到x点的最少代价 d[x][1]表示x点向下走但不回到x点的最少代价 d[x][2]表示x点向下走的最长路 d[x][3]表示x点向下走的次长路 u[x][0]表示x点 ...

  3. No FileSystem for scheme: 远程访问HDFS找不到shceme

    问题描述: hadoop版本:hadoop-2.0.0-cdh4.3.0 在本地环境下能够找到scheme,但是通过maven打包fatjar 后放到其他机器上就出现找不到scheme. 看了代码,发 ...

  4. NOIP200002税收与补贴

    试题描述 每样商品的价格越低,其销量就会相应增大.现已知某种商品的成本及其在若干价位上的销量(产品不会低于成本销售),并假设相邻价位间销量的变化是线性的且在价格高于给定的最高价位后,销量以某固定数值递 ...

  5. 2016.03.31,英语,《Vocabulary Builder》Unit 08

    tend/tent: from the Latin tendere, meaning 'to stretch, extend, or spread'. tent: [tent] n. 帐篷 vt.&a ...

  6. [办公自动化]如何对Excel表格顶部设计

    领导有一个excel要完成如下功能:顶部要包含企业LOGO,还要包含设计图号.版次等表格,还要包含类似“第  页 of  页” 总体思路: 1.利用顶端标题行完成除了页码以外的所有事情:(当然也可以利 ...

  7. MySQL 数据库设计 笔记与总结(1)需求分析

    数据库设计的步骤 ① 需求分析 ② 逻辑设计 使用 ER 图对数据库进行逻辑建模 ③ 物理设计 ④ 维护优化 a. 新的需求进行建表 b. 索引优化 c. 大表拆分 [需求分析] ① 了解系统中所要存 ...

  8. 以http形式启动uwsgi服务

    uwsgi yourfile.ini # 配置文件 [uwsgi] http = 127.0.0.1:3106 socket = 127.0.0.1:3006 chdir = /www/student ...

  9. Failed to connect to remote VM. Connection refused. Connection refused: connect.

    eclipse debug启动经常出现这个错误,已经启动了debug进程,X掉重新启动即可.

  10. DirectX 基础学习系列5 纹理映射

    1 纹理坐标 类似BMP图像坐标系,左上为原点 纹理坐标为了规范化,范围限定在[0,1]之间,使用纹理的时候,需要修改顶点结构 struct ColorVetex { float x, y,z; fl ...