1、单元测试
概念: 针对最小的功能单元编写测试代码。
最小单元:方法。
常用的测试方法:使用main()来进行测试,但main函数测试有很多缺点,很难编写一组通用的测试代码。因此,测试框架应运而生。
JUnit
是一个由java语言开发的开源单元测试框架,为Java设计,使用JUnit可以简单的组织测试代码,并且生成测试报告。
1.1 使用
测试方法:
- assertEquals(1, 方法);//期望方法返回值为1
- assertTrue();
- assertFlase();
- assertNotNull();
- assertArrayEquals();
- assertThrows();//捕获指定异常
编写单元测试代码的规范
- 简单易懂
2.相互独立,不依赖运行顺序
3.测试边界条件
4.使用@Test注解
1.2 Fixture
作用:
编写测试前准备、测试后清理的固定代码。
使用:
使用@BeforeEach与@AfterEach注释,before用于在@Test运行之前初始化变量,after用于在@Test之后清理测试资源,它们会在每个@Test标注的方法的前后运行。
使用@BeforeAll和@BeforeAll,只能初始化静态变量,在所有@Test注释标注的方法前后仅运行一次。
1.3 条件测试
跳过某些测试方法时,可以添加@Disable注解,这个测试方法就不会被执行。
@Disabled
@Test
void test() {
//do something
}
不在Windows平台执行的测试
@DisabledOnOs(OS.WINDOWS)
@Test
void test() {
//do something
}
只能在Java 9或更高版本执行的测试
@DisabledOnJre(JRE.JAVA_8)
@Test
void test() {
//do something
}
只能在64位操作系统上执行的测试
@DisabledIfSystemProperty(named="os.arch", matches=".*64.*")
@Test
void test() {
//do something
}
需要传入环境变量DEBUG=true才能执行的测试
@DisabledIfEnvironmentVariable(named="DEBUG", matches="true")
@Test
void test() {
//do something
}
@EnableIf,根据反悔的boolean值决定是否执行测试
@DisableIf("....")
@Test
void test() {
//do something
}
1.3 参数化测试
用处:
使用一组参数来对方法进行测试.
第一种方法:使用@ParameterrizedTest
注解来进行参数化测试
@ParameterizedTest
@ValueSource(ints = {0, 12, 4, 3})
void add(int a){
return a + 1;
}
当传入参数个数大于1时,简单的@ParameterrrizedTest已经不能再适用。可以使用@MethodSource注解
@ParameterizedTest
@ValueSource(ints = {0, 12, 4, 3})
void add(int a, int b){
return a + b;
}
//返回一组测试参数
static List<Arguments> add(){
return List.of(
Arguments.arguments(1,2);
Arguments.arguments(2,2);
Arguments.arguments(6,8);
Arguments.arguments(5,3);
);
}
第二种方法:使用@CsvFileSource注解
@ParameterizedTest
@CsvSource({1,4,5,5,6,3,3,6,5,2})
void add(int a, int b){
return a + b;
}
第三种方法,当数据量较大时,可以使用Csv文件,使用注解@CsvFileSource,需要注意的是csv文件必须放在test目录下,因为JUnit只在classpath中查找csv。
2、XML
简介:
可扩展标记语言(eXtensible Markup Language),一种数据表示格式,可以描述非常复杂的数据结构,常用于传输和存储数据,配置文件。
特点:
- 纯文本,默认使用utf-8编码
- 可嵌套,适用于结构化数据
- 常通过网络作为消息传输
- 具有固定结构
2.1 XML结构
xml具有固定的格式,首行必须是<?xml version="1.0"?>, 一个xml文档仅有一个根元素,根元素可以包含任意个子元素。验证一个XML文档的正确性,可以将其拖至浏览器验证,浏览器对xml没有容错性,不同于html文档,缺少关闭标签也能被解析。
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE note SYSTEM "book.dtd">
<book id="1">
<name>Java核心技术</name>
<author>Cay S. Horstmann</author>
<isbn lang="CN">1234567</isbn>
<tags>
<tag>Java</tag>
<tag>Network</tag>
</tags>
<pubDate/>
</book>
2.2 解析XML文档
2.2.1 使用DOM
Java提供快乐DOM API来(Document Object Model)解析XML, 并在内存中表示为树形结构。
优点:
方便省事。
缺点:
占用内存大。
主要对象:
- Document: 代表整个XML文档
- Element:代表一个XML元素
- Attribute:代表一个元素的某个属性
获取一个Document对象,可以遍历所有的子节点,获取所有元素,属性,文本数据,注释等。这些节点统称为Node,每个Node都有自己的Type,根据Type来区分一个Node到底是元素还是属性等等。
InputStream input = Main.class.getResourceAsStream("/book.xml");
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
DocumentBuilder db = dbf.newDocumentBuilder();
Document doc = db.parse(input);
void printNode(Node n, int indent) {
for (int i = 0; i < indent; i++) {
System.out.print(' ');
}
switch (n.getNodeType()) {
case Node.DOCUMENT_NODE: // Document节点
System.out.println("Document: " + n.getNodeName());
break;
case Node.ELEMENT_NODE: // 元素节点
System.out.println("Element: " + n.getNodeName());
break;
case Node.TEXT_NODE: // 文本
System.out.println("Text: " + n.getNodeName() + " = " + n.getNodeValue());
break;
case Node.ATTRIBUTE_NODE: // 属性
System.out.println("Attr: " + n.getNodeName() + " = " + n.getNodeValue());
break;
default: // 其他
System.out.println("NodeType: " + n.getNodeType() + ", NodeName: " + n.getNodeName());
}
for (Node child = n.getFirstChild(); child != null; child = child.getNextSibling()) {
printNode(child, indent + 1);
}
}