Junit单元测试笔记

什么是单元测试?

单元测试

单元测试是针对最小的功能单元编写测试代码,而Java程序中最小的功能单元是方法,单元测试就是针对单个java方法的测试。

单元测试的优势

  • 确保单个方法运行正常
  • 如果修改了某个方法代码,只需确保对应的单元测试通过即可
  • 测试代码本身可以作为示例代码
  • 可以自动化运行所有测试并获得报告

TDD测试驱动开发

测试驱动开发(Test-Driven Development)

测试驱动开发是敏捷开发中的一项核心实践和技术,也是一种设计方法论。TDD的原理是在开发功能代码之前,先编写单元测试用例代码,测试代码确定需要编写什么产品代码。

在这里插入图片描述

为什么要使用Junit?

通常情况下,当我们写好了一种方法之后要确认方法的正确性时,我们会在main函数中设计一个测试用例,并且调用方法测试,检测方法是否正确。使用main方法进行测试就代表着每写一个方法就要在main方法内写一个测试代码,然后测试下一个方法时又要注释或删掉上一个方法的测试代码,这样就极其不方便。

比如在类中有加,减两种方法

public class TestJunit {

    public static int  addNums(int a,int b){//为了在main方法内调用方便设为static,后续测试没有使用static修饰加减两种方法
        return a+b;
    }
    public static int  minusNums(int a,int b){
        return a-b;
    }
}

此时对加进行测试,将1+5=6作为测试用例

public static void main(String[] args) {
    int test1=addNums(1,5);//6,正确
    System.out.println(test1);
}

那么再对减进行测试,1-5=-4作为测试用例,就需要注释掉上一步的内容

public static void main(String[] args) {
    //int test1=addNums(1,5);//6,正确
    //System.out.println(test1);
    int test2=minusNums(1,5);//-4,正确
    System.out.println(test2); 
}

这样很不方便,如果通过Junit进行测试就不需要重复的写测试代码再注释掉测试代码了

使用Junit的步骤

  1. 在项目中建立测试类

    在这里插入图片描述

  2. 在测试类中输入 @Test注解,刚开始注解会报红,此时只需要在系统提示的操作下导入Junit的包即可

  3. 编写测试类

    public class TestDemo {
        @Test
        public void Test1(){
            TestJunit testJunit = new TestJunit();
            int ans=testJunit.addNums(1,5);
            System.out.println(ans);
        }
        @Test
        public void Test2(){
            TestJunit testJunit=new TestJunit();
            int ans=testJunit.minusNums(1,5);
            System.out.println(ans);
        }
    }
    
  4. 运行测试类
    在这里插入图片描述

  5. 此时两个测试用例成功运行,并输出正确结果

断言

Junit提供了辅助函数去帮助我们验证预期结果和实际结果是否相同,这种辅助函数称为断言

断言参数解释
assertEquals([String message],expected,actual)message是可选的参数,如果报错会报告这个message
expected是期望值,通常是用户指定的内容,actual是测试代码返回的实际值
该断言用于判断预期值和实际值是否相等
assertEquals([String message],expected,actual,tolerance)message是可选的参数,如果报错会报告这个message
expected是期望值,通常是用户指定的内容,actual是测试代码返回的实际值
tolerance是误差参数,参加比较的两个数在这个误差内被认为是相等的
该断言用于判断预期值与实际值是否在规定的误差区间内,是则认为相等
assertTrue ([String message],Boolean condition)message是可选的参数,如果报错会报告这个message
condition是待验证的布尔值
该断言用来验证给定的布尔值是否为真,假如结果为假则验证失败
assertFalse([String message],Boolean condition)message是可选的参数,如果报错会报告这个message
condition是待验证的布尔值
该断言用来验证给定的布尔值是否为假,假如结果为真则验证失败
assertNull([String message],Object object)message是可选的参数,如果报错会报告这个message
object是待验证的对象
该断言用来验证给定的对象是否为Null,假如不为Null则验证失败
assertNotNull([String message],Object object)message是可选的参数,如果报错会报告这个message
object是待验证的对象
该断言用来验证给定的对象是否不为Null,假如为Null则验证失败
assertSame ([String message], expected,actual)message是可选的参数,如果报错会报告这个message
expect是期望值,actual是测试代码返回的实际值
该断言用来验证expected和actual参数所引用的是否是同一个对象,假如不是同一个对象则验证失败。
assertNotSame ([String message], expected,actual)message是可选的参数,如果报错会报告这个message
expect是期望值,actual是测试代码返回的实际值
该断言用来验证expected和actual参数所引用的是否是不同对象,假如是同一个对象则验证失败。
Fail([String message])message是可选的参数,如果报错会报告这个message
该断言用来使测试失败,通常用在测试不能到达的分支上

注解

注解名用途
@Test表示该方法是一个测试方法 测试方法必须为public void
@Before在运行多个测试方法时,可能会在数据准备或其他准备中执行一段相同的代码,那么可以将这段可公用的代码提取出来,作为一个方法a并注解@Before,@Before和@BeForeClass的区别是每个测试方法运行前都执行一次这个方法a ,该方法必须为public void,不能为static;比如初始化测试对象 input=new FileInputStream();
@BeforeClass在运行多个测试方法时,可能会在数据准备或其他准备中执行一段相同的代码,那么可以将这段可公用的代码提取出来,作为一个方法a并注解@BeforeClass,那么在所有测试方法运行前会先运行一次这个方法a,该方法必须是public static void;一般是初始化非常耗时的资源,比如创建数据库
@After与@Before类似,主要用于注解运行测试类之后再运行的方法,比如销毁@Before创建的测试对象 input.close()
@AfterClass与@BeforeClass类似,但是顺序不同,比如删除数据库
@Runwith放在测试类名前,用来确定这个类怎么运行,指定测试运行器。
@Ignore暂不运行某些测试方法或类,在测试方法前加上@Ignore注解,Junit会统计Ignore次数
@Parameters用于参数化功能

使用注解和断言之后的代码为

public class TestDemo {
    TestJunit testJunit;//定义测试对象
    @Before
    public void beforeMethod(){
        testJunit=new TestJunit();//初始化测试对象
        System.out.println("before");
    }
    @Test
    public void Test1(){
        int ans=testJunit.addNums(1,5);
        Assert.assertEquals("ErrorTest1",6,ans);
    }
    @Test
    public void Test2(){
        int ans=testJunit.minusNums(1,5);
        Assert.assertEquals("ErrorTest2",-4,ans);
    }
    @After
    public void afterMethod(){
        System.out.println("after");
    }
}

运行结果

在这里插入图片描述

如果修改代码,让Test1的Assert.assertEquals(“ErrorTest1”,6,ans);预期结果为7,此时预期结果是错误的,实际结果6是对的,但是他们不相同,测试就会报错

在这里插入图片描述

可以看到虽然Test1出现错误,但是Test2是没有受影响的,并且很清楚的告诉我们哪里出现的错误。

注意:如果预期与实际值相同,是不会输出message的内容的

参数化测试

参数化测试可以使用不同的值反复运行同一个测试

  1. 创建一个判断是否是偶数的方法

    public  boolean isEven(int i){
        return i%2==0?true:false;
    }
    
  2. 在测试类上注解@RunWith(Parameterized.class)

    @RunWith(Parameterized.class)
    public class TestDemo {}
    
  3. 创建@Parameters注释的公共静态方法,返回一个对象的集合来作为测试数据集合

    @Parameterized.Parameters
    public static Collection Numbers(){
        return Arrays.asList(new Object[][]{
                {1,false},
                {2,true},
                {12,true},
                {18,true},
                {35,false},
                {36,true}
        });
    }
    
  4. 创建一个公共的构造函数,它接收和一行测试数据相等同的东西

  5. 为每一列测试数据创建一个实例变量

  6. 用实例变量作为测试数据来源来创建测试用例

代码:

@RunWith(Parameterized.class)
public class TestDemo {
    TestJunit testJunit;//定义测试对象
    private Boolean expected;//定义预期的布尔值
    private Integer numbers;//定义输入的数据

    @Before
    public void beforeMethod(){
        testJunit=new TestJunit();//初始化测试对象
        System.out.println("before");
    }
    public TestDemo(Integer numbers,Boolean expected){//构造函数
        this.numbers=numbers;
        this.expected=expected;
    }
    @Parameterized.Parameters
    public static Collection Numbers(){//测试所需数据集
        return Arrays.asList(new Object[][]{
                {1,false},
                {2,true},
                {12,true},
                {18,true},
                {35,false},
                {36,true}
        });
    }
    @Test
    public void TestisEven(){//测试方法
        boolean ans=testJunit.isEven(numbers);
        Assert.assertEquals(expected,ans);
    }
    @After
    public void afterMethod(){
        System.out.println("after");
    }
}

在这里插入图片描述

可以看到每一组数据都运行正常且每组测试的运行都会执行before和after

超时测试

@Test(timeout=1000),表示超时时间为1000毫秒,timeout的单位为毫秒

@Test(timeout = 1000)
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值