IDEA Maven项目利用Junit4进行单元测试

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/YF_Li123/article/details/83004095

    最近在开发项目的时候需要写单元测试,之前一直没有接触过,于是从零开始入门学习,查了网上相关资料,总结成为笔记,在此感谢各位大佬的详细资料!!!

目录

0、背景

1、单元测试简介

2、实践

(1)创建项目

(2)创建Junit_Test_Demo的单元测试

(3)运行单元测试

补充:

1、关于Junit_Test_DemoTest需要注意:

2、几个常用的注解

3、@Test的一些属性

4、代码覆盖率


 

0、背景

    我们在写好一个函数或者类以后,需要检验我们的程序是否存在bug或者是否满足我们的需求,通常的做法就是将写好的函数在mian方法中调用,输入一些测试用例进行检验。当要检验的方法数量较少时,这种方法可行,但是当我们有大量的函数需要验证时,该方法就显得笨重且繁琐,往往需要我们人工检查输出的结果是否正确等,比较混乱。因此,单元测试就是用来解决这种繁琐问题的。

1、单元测试简介

    单元测试是对一个函数、一个类、一个模块甚至是一个系统进行正确性检验对过程。

2、实践

(1)创建项目

我创建的项目名称为junit_test_demo,并创建了一个名为Junit_Test_Demo的类,添加如下代码:

public class Junit_Test_Demo {

    // 加法
    public int add(int a, int b) {
        return a + b;
    }

    // 减法
    public int subtract(int a, int b) {
        return a - b;
    }

    // 乘法
    public int multiply(int a, int b) {
        return a * b;
    }

    // 除法
    public double divide(int a, int b) throws Exception {
        if (b == 0) {
            throw new Exception("除数不能为零!");
        }
        else {
            return a / b;
        }
    }
}

(2)创建Junit_Test_Demo的单元测试

A. 配置junit4的Maven依赖

在pom.xml文件中添加如下内容,并设置自动导入项目依赖:

<dependencies>
    <dependency>
        <groupId>junit</groupId>
        <artifactId>junit</artifactId>
        <version>4.12</version>
        <scope>test</scope>
    </dependency>
</dependencies>

B.  将光标置于要添加单元测试的类名上,使用Cmd+shift+T快捷键,选择Create New Test...

C.  在弹出的对话框中勾选要添加单元测试的函数,点击OK

D.  此时会在项目的test目录下创建相应的单元测试类(一般命名规则:类名+Test),如Junit_Test_DemoTest,然后在相应的函数中添加测试代码如下:

import org.junit.After;
import org.junit.Before;
import org.junit.Test;

import static org.junit.Assert.*;

public class Junit_Test_DemoTest {

    @Before
    public void setUp() throws Exception {
        System.out.println("单元测试开始前相关操作...");
    }

    @After
    public void tearDown() throws Exception {
        System.out.println("单元测试结束后相关操作...");
    }

    @Test
    public void add() {
        /**
         * assertEquals函数
         * first param: Expected value  期望返回值
         * second param: Actual value   实际返回值
         */
        assertEquals(8, new Junit_Test_Demo().add(2,6));
    }

    @Test
    public void subtract() {
        assertEquals(7, new Junit_Test_Demo().subtract(9,2));
    }

    @Test
    public void multiply() {
        assertEquals(36, new Junit_Test_Demo().multiply(6,6));
    }

    @Test
    public void divide() throws Exception {
        /**
         * assertEquals函数
         * first param: Expected value  期望返回值
         * second param: Actual value   实际返回值
         * third param: delta value     误差范围,因为double或float类型值无法直接进行比较,满足一定误差范围即认为两者相等
         */
        assertEquals(2, new Junit_Test_Demo().divide(8,4),0.001);
    }
}

(3)运行单元测试

A. 点击Run Junit_Test_DemoTest,如果没有错误,全部测试通过,运行结果如下:

B. 下面我们修改一下multiply的测试数值,将第一个6改成4,目的让测试不通过,看会是什么结果:提示1个测试失败,3个通过,并给出了失败的详细原因。

 

未完待续。。。


补充:

1、关于Junit_Test_DemoTest需要注意:

(1)所有测试方法返回类型必须是void且无参数;

(2)一个方法之所以为测试方法,是由@Test来注解的;

(3)assertEquals方法作用是比较两个参数是否相等,测试的时候应该多选几个测试数值,比如临界值等;

(4)assertEquals方法不止可以比较两个int型参数,还可以比较其它类型参数,有多种重载形式;

2、几个常用的注解

(1)@Test:将一个方法标记为测试方法;

(2)@Before:每一个测试方法调用前必执行的方法;

(3)@After:每一个测试方法调用后必执行的方法;

(4)@BeforeClass:所有测试方法调用前执行一次,在测试类没有实例化之前就已被加载,需用static修饰;

(5)@AfterClass:所有测试方法调用后执行一次,在测试类没有实例化之前就已被加载,需用static修饰;

(6)@Ignore:暂不执行该方法;

 

现在我们来测试一下每个注解,修改单元测试类Junit_Test_DemoTest,修改内容如下:

  • 增加一个构造函数Junit_Test_DemoTest;

  • 增加函数setUpBeforeClass,并用@BeforeClass注解;

  • 增加函数setUpAfterClass,并用@AfterClass注解;

  • 将测试函数multiply用@Ignore注解;

import org.junit.*;

import static org.junit.Assert.*;

public class Junit_Test_DemoTest {

    public Junit_Test_DemoTest() {
        System.out.println("构造函数...");
    }

    @BeforeClass
    public static void  setUpBeforeClass() {
        System.out.println("BeforeClass...");
    }

    @AfterClass
    public static void setUpAfterClass() {
        System.out.println("AfterClass...");
    }

    @Before
    public void setUp() throws Exception {
        System.out.println("单元测试开始前相关操作...");
    }

    @After
    public void tearDown() throws Exception {
        System.out.println("单元测试结束后相关操作...");
    }

    @Test
    public void add() {
        /**
         * assertEquals函数
         * first param: Expected value  期望返回值
         * second param: Actual value   实际返回值
         */
        assertEquals(8, new Junit_Test_Demo().add(2,6));
    }

    @Test
    public void subtract() {
        assertEquals(7, new Junit_Test_Demo().subtract(9,2));
    }

    @Ignore
    public void multiply() {
        assertEquals(36, new Junit_Test_Demo().multiply(6,6));
    }

    @Test
    public void divide() throws Exception {
        /**
         * assertEquals函数
         * first param: Expected value  期望返回值
         * second param: Actual value   实际返回值
         * third param: delta value     误差范围,因为double或float类型值无法直接进行比较,满足一定误差范围即认为两者相等
         */
        assertEquals(2, new Junit_Test_Demo().divide(8,4),0.001);
    }
}

运行结果如下:

从结果中得知:

  • @BeforClass和@AfterClass在构造方法前被调用了,且只调用了一次,一般用来初始化和关闭资源;

  • @Before和@After在每个@Test执行前后被调用

  • @Ignore被忽略;

  • 构造函数执行了三次、三次、三次,这是为什么?这是因为Junit4为了保证每个测试方法都是单元测试,互不影响,在每个测试方法被调用前都会初始化出一个新的实例对象来执行。

3、@Test的一些属性

  • excepted属性

excepted属性是用来测试异常的,即如果被测试的方法没有抛出异常,测试不通过,抛出异常,则测试通过。

我们在单元测试类中添加异常测试方法:

@Test (expected = Exception.class)
    public void testDivideException() throws Exception {
        new Junit_Test_Demo().divide(3,0);
        fail("除数为零没有抛出异常");
    }

    该测试方法是(expected = Exception.class)和fail(“除数为零没有抛出异常”),会检查是否抛出Exception异常(也可以检查其他异常)。如果抛出异常测试通过,没有抛出异常测试不通过执行fail(“除数为零没有抛出异常”)。

  • timeout属性

该方法是用来测试性能的,测试一个方法能不能在规定时间内完成。用法和expected一样。

 @Test (timeout = 1000)
    public void testDivideTimeout() throws Exception {
        new Junit_Test_Demo().divide(6,3);
    }

4、代码覆盖率

    收集覆盖率,通过Run→Run ‘Junit_Test_DemoTest’ with Coverage,运行结束后,IDEA将会在Projec工具窗口显示每个程序包、类的覆盖率数据,同时在Coverage工具窗和编辑器中也会显示。

 

参考资料:

[1]: https://blog.csdn.net/u011138533/article/details/52165577

[2]: https://blog.csdn.net/chenbetter1996/article/details/80441178

展开阅读全文

没有更多推荐了,返回首页