实验内容

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

实验要求

  1. 没有Linux基础的同学建议先学习《Linux基础入门(新版)》《Vim编辑器》 课程
  2. 完成实验、撰写实验报告,实验报告以博客方式发表在博客园,注意实验报告重点是运行结果,遇到的问题(工具查找,安装,使用,程序的编辑,调试,运行等)、解决办法(空洞的方法如“查网络”、“问同学”、“看书”等一律得0分)以及分析(从中可以得到什么启示,有什么收获,教训等)。报告可以参考范飞龙老师的指导
  3. 严禁抄袭,有该行为者实验成绩归零,并附加其他惩罚措施。

实验步骤

一、单元测试

三种代码
要了解并养成用写三种代码来编程的习惯

  • 伪代码
  • 产品代码
  • 测试代码

举个例子:我们要在一个MyUtil类中解决一个百分制成绩转成“优、良、中、及格、不及格”五级制成绩的功能。

先写伪代码,伪代码与具体编程语言无关,不要写与具体编程语言语法相关的语句,伪代码从意图层面来解决问题,最终,伪代码产品代码最自然的、最好的注释。

百分制转五分制:
如果成绩小于60,转成“不及格”
如果成绩在60与70之间,转成“及格”
如果成绩在70与80之间,转成“中等”
如果成绩在80与90之间,转成“良好”
如果成绩在90与100之间,转成“优秀”
其他,转成“错误”

写完伪代码后,就可以用特定的编程语言翻译一下,就是可用的产品代码了。这里使用JavaMyUtil.java:

public class MyUtil{
public static String percentage2fivegrade(int grade){
//如果成绩小于60,转成“不及格”
if (grade < )
return "不及格";
//如果成绩在60与70之间,转成“及格”
else if (grade < )
return "及格";
//如果成绩在70与80之间,转成“中等”
else if (grade < )
return "中等";
//如果成绩在80与90之间,转成“良好”
else if (grade < )
return "良好";
//如果成绩在90与100之间,转成“优秀”
else if (grade < )
return "优秀";
//其他,转成“错误”
else
return "错误";
}
}

一般来说产品代码出来后,大部分工作可以说是完成了,但是,谁能保证你的产品代码不会出现bug或者错误呢?所以这个时候就需要编写测试代码,通过测试代码能够更好的完善最后的产品代码~

在IDEA中我们可以借助单元测试工具JUnit来辅助进行TDD,直接点击Create Test就可以了

而且,测试代码仅测试一种情况往往是不够的,通常来说会进行三个方面的测试:
正常情况

import org.junit.Test;
import junit.framework.TestCase;
public class MyUtilTest extends TestCase {
@Test
public void testNormal() {
assertEquals("不及格", MyUtil.percentage2fivegrade());
assertEquals("及格", MyUtil.percentage2fivegrade());
assertEquals("中等", MyUtil.percentage2fivegrade());
assertEquals("良好", MyUtil.percentage2fivegrade());
assertEquals("优秀", MyUtil.percentage2fivegrade());
}
}

异常情况

import org.junit.Test;
import junit.framework.TestCase;
public class MyUtilTest extends TestCase {
@Test
public void testException() {
assertEquals("错误", MyUtil.percentage2fivegrade(-));
assertEquals("错误", MyUtil.percentage2fivegrade());
}
}

边界情况

import org.junit.Test;
import junit.framework.TestCase;
public class MyUtilTest extends TestCase {
@Test
public void testBoundary() {
assertEquals("不及格", MyUtil.percentage2fivegrade());
assertEquals("及格", MyUtil.percentage2fivegrade());
assertEquals("中等", MyUtil.percentage2fivegrade());
assertEquals("良好", MyUtil.percentage2fivegrade());
assertEquals("优秀", MyUtil.percentage2fivegrade());
assertEquals("优秀", MyUtil.percentage2fivegrade());
}
}
  • 如果测试通过就会显示test passed

  • 如果测试没通过,则会显示红色,并显示test failed,而且会告知哪里出了错误

通过最后的测试代码的成功测试后,我们的产品代码才算是真正的完工了。当然,测试代码的编写不能随意,应该尽可能地考虑周全,才能很好的完善产品代码

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

1.先写测试代码,再写产品代码的TDD的一般步骤如下:

  • 明确当前要完成的功能,记录成一个测试列表
  • 快速完成编写针对此功能的测试用例
  • 测试代码编译不通过(没产品代码呢)
  • 编写产品代码
  • 测试通过
  • 对代码进行重构,并保证测试通过(重构下次实验练习)
  • 循环完成所有功能的开发

2.TDD的编码节奏是:

  • 增加测试代码,JUnit出现红条
  • 修改产品代码
  • JUnit出现绿条,任务完成

3.老师给的StringBuffer 的例子 积极主动敲代码,使用JUnit学习Java

public class StringBufferDemo{
public static void main(String [] args){
StringBuffer buffer = new StringBuffer();
buffer.append('S');
buffer.append("tringBuffer");
System.out.println(buffer.length());
System.out.println(buffer.charAt());
System.out.println(buffer.capacity();
System.out.println(buffer.indexOf("tring"));
System.out.println("buffer = " + buffer.toString());
}
}

首先我们需要改写一下例子中的程序,使其能够使用TDD来测试。改代码之前我们得知道StringBufferDemo类中的方法都是什么功能,才能知道我们需要测试哪些内容。通过查阅资料,得知

  • StringBuffer( ):分配16个字符的缓冲区
  • length():返回字符串的长度
  • charAt(int i) :返回此序列中指定索引处的 char 值。第一个 char 值在索引 0 处,第二个在索引 1 处,依此类推
  • capacity():返回string分配的存储容量
  • indexOf(String s):返回输入的子字符串的第一个字母在母字符串的位置

最后的出的产品代码:

public class StringBufferDemo{
StringBuffer buffer = new StringBuffer();
public StringBufferDemo(StringBuffer buffer){
this.buffer = buffer;
}
public Character charAt(int i){
return buffer.charAt(i);
}
public int capacity(){
return buffer.capacity();
}
public int length(){
return buffer.length();
}
public int indexOf(String buf) {
return buffer.indexOf(buf);
}
}

通过IDEA中的TDD写出的测试代码:

import junit.framework.TestCase;
import org.junit.Test;
public class StringBufferDemoTest extends TestCase {
StringBuffer a = new StringBuffer("zhuyueniupi");//(<=16)
StringBuffer b = new StringBuffer("zhuyueniupizhuyueniupi");//(>16&&<=34)
StringBuffer c = new StringBuffer("zhuyueniupizhuyueniupizhuyueniupi");//(>=34)
@Test
public void testcharAt() throws Exception{
assertEquals('z',a.charAt());
assertEquals('u',a.charAt());
assertEquals('p',a.charAt());
assertEquals('i',a.charAt());
}
@Test
public void testcapacity() throws Exception{
assertEquals(,a.capacity());
assertEquals(,b.capacity());
assertEquals(,c.capacity());
}
@Test
public void testlength() throws Exception{
assertEquals(,a.length());
assertEquals(,b.length());
assertEquals(,c.length());
}
@Test
public void testindexOf() throws Exception{
assertEquals(,a.indexOf("zh"));
assertEquals(,a.indexOf("yueniu"));
assertEquals(,a.indexOf("iupi"));
}
}

测试运行截图:

三、面向对象三要素

  • 抽象
    程序设计中,抽象包括两个方面,一是过程抽象,二是数据抽象

例如:打印“1-100”这种大数据的时候

public void printn(int n){
for(int i=; i<=n; i++)
System.out.println(n);
}

而且能够快速打印

printn();
    • 封装、继承与多态
      面向对象(Object-Oriented)的三要素包括:封装、继承、多态。
      包括:面向对象分析(OOA)、面向对象设计(OOD)、面向对象编程实现(OOP)

    • 设计模式初步
      S.O.L.I.D原则:
    • SRP(Single Responsibility Principle,单一职责原则)
    • OCP(Open-Closed Principle,开放-封闭原则)
    • LSP(Liskov Substitusion Principle,Liskov替换原则)
    • ISP(Interface Segregation Principle,接口分离原则)
    • DIP(Dependency Inversion Principle,依赖倒置原则)

四、练习

  • 要求:使用TDD的方式设计关实现复数类Complex
  • 伪代码:
// 定义属性并生成getter,setter
double RealPart;
double ImagePart;
// 定义构造函数
public Complex()
public Complex(double R,double I)
//Override Object
public boolean equals(Object obj)
public String toString()
// 定义公有方法:加减乘除
Complex ComplexAdd(Complex a)
Complex ComplexSub(Complex a)
Complex ComplexMulti(Complex a)
Complex ComplexDiv(Complex a)
  • 产品代码:
public class Complex {
// 定义属性并生成getter,setter
private double r;
private double i;
// 定义构造函数
public Complex(double r,double i){
this.r=r;
this.i=i;
}
public static double getRealPart(double r){
return r;
}
public static double getImagePart(double i){
return i;
}
//Override Object
public boolean equals(Object obj){
Complex complex=(Complex) obj;
if (complex.r!=r) {
return false;
}
if(complex.i!=i){
return false;
}
return true;
}
public String toString(){
String str=new String();
if (i==) str=r+"";
else if(i<) str=r + ""+i+"i";
else str=r+""+"+"+i+"i";
return str;
}
// 定义公有方法:加减乘除
Complex ComplexAdd(Complex a){
return new Complex(r+a.r,i+a.i);
}
Complex ComplexSub(Complex a){
return new Complex(r-a.r,i-a.i);
}
Complex ComplexMulti(Complex a){
return new Complex(ra.r-ia.i,ra.i+ia.r);
}
Complex ComplexDiv(Complex a){
return new Complex((ra.r+ia.i)/(a.ra.r+a.ia.i),(ia.r-ra.i)/(a.ra.r+a.ia.i));
}
}
  • 测试代码:
import junit.framework.TestCase;
import org.junit.Test;
public class ComplexTest extends TestCase {
Complex a=new Complex(,);
Complex b=new Complex(-,-);
Complex c=new Complex(,-);
Complex d=new Complex(,-);
@Test
public void testequals(){
assertEquals(false,a.equals(b));
assertEquals(false,b.equals(c));
assertEquals(true,c.equals(d));
}
@Test
public void testAdd(){
assertEquals(new Complex(-,),a.ComplexAdd(b));
assertEquals(new Complex(,),a.ComplexAdd(c));
}
@Test
public void testSub(){
assertEquals(new Complex(,),a.ComplexSub(b));
assertEquals(new Complex(-,),a.ComplexSub(c));
}
@Test
public void testMulti(){
assertEquals(new Complex(,-),a.ComplexMulti(b));
assertEquals(new Complex(,),a.ComplexMulti(c));
}
@Test
public void testDiv(){
assertEquals(new Complex(,0.5),a.ComplexDiv(c));
assertEquals(new Complex(-0.3,-0.4),b.ComplexDiv(c));
}
}

五、实验中遇到的问题

在使用Junit的时候,import junit.framework.TestCase; 中的Junit 显示红色

提示是程序包org.junti不存在,后来通过百度查找解决了这个问题

  • @Test 是红色的
    在老师的博客中有解决方法

直接File 中点击Project Structure ,然后找到Modules 里的Dependencies 添加junit.jar

其中对于junit.jar 的地址查询可以用Everything软件快捷查到

PSP(Personal Software Process)时间


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

2018-2019-2 20175236实验二《Java面向对象程序设计》实验报告的更多相关文章

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

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

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

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

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

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

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

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

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

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

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

    实验二 Java面向对象程序设计 实验内容 1.初步掌握单元测试和TDD 2.理解并掌握面向对象三要素:封装.继承.多态 3.初步掌握UML建模 4.熟悉S.O.L.I.D原则 5.了解设计模式 实验 ...

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

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

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

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

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

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

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

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

随机推荐

  1. VUE处理 组件赋值 watch 监听不到赋值问题

    开发中,遇到了一个BUG,做的页面类似于 导航切换效果.两个组件传值. 上方导航组件   (主动) 左侧导航组件   (被动) 点击上方导航,左侧导航实现变换对应的栏目. 实现过程中,遇到了点问题.左 ...

  2. iOS跳转第三方应用举例一号店和京东

    1.首先要跳转到第三方应用都需要知道第三方应用的scheme,虽然百度能得到很多,但是不乏一些新增的或者改了的,怎么获得APP的scheme,鉴于现在iTunes不好用了,介绍一个app ---app ...

  3. 在vue.js 中使用animate.css库

    main.js文件引入后,在vue文件里直接添加class   animated bounceInUp

  4. C#中的抽象类、抽象方法和虚方法

    [抽象类]abstract 修饰符可与类和方法一起使用定义抽象类的目的是提供可由其子类共享的一般形式.子类可以根据自身需要扩展抽象类.抽象类不能实例化.抽象方法没有函数体.抽象方法必须在子类中给出具体 ...

  5. js常用随手记

    1. 判断是否是空对象 let myObject={} Object.keys(myObject).length 2. void 0 代替 undefined undefined 不是保留字,在局部作 ...

  6. Fiddler实现手机抓包——小白入门

    方法1:https://www.cnblogs.com/hzg1981/p/5610530.html 方法2:转载自:http://blog.csdn.net/gld824125233/article ...

  7. Podfile

    platform :ios, "9.0" target "APPName" dopod 'AFNetworking'pod 'SVProgressHUD'pod ...

  8. PHP 多维数组排序 函数怎么保持数字键不被重新索引

    /** * 根据数组中的某个键值大小进行排序,仅支持二维数组 * * @param array $array 排序数组 * @param string $key 键值 * @param bool $a ...

  9. 【软件构造】-<笔记>-浅谈java中类的初始化过程

    编写java程序时,每创建一个新的对象,都会对对象的内容进行初始化. 每一个类的方法中的局部变量都有严格的初始化要求,因此假如写出下面的程序: void f(){ int i; i++; } 编译时就 ...

  10. python学习|类和实例

    什么叫实例对象呢?大家可以想象一下,[类]就像工厂的模具,以它为模板,造出来的成千上万的产品,才是被我们消费.购买.使用,真正融入我们生活的东西.这些产品,在Python中就叫[实例对象]. 往深了说 ...