当前位置: 首页 > news >正文

java单元测试( Hamcrest 断言)

java单元测试( Hamcrest 断言)

单元测试特征:
1 范围狭窄
2 限于单一类或方法
3 体积小

为什么要编写单元测试?
为了防止错误(很明显!)
而且还可以提高开发人员的生产力,因为单元测试:
(1) 帮助实施——在编码的同时编写测试可以快速反馈正在编写的代码。
(2) 失败时应该易于理解——每个测试在概念上都应该简单,并专注于系统的特定部分。
(3) 作为工程师如何使用被测系统部分的文档和示例(因为书面文档很快就会无可救药地过时)。
在谷歌,80% 的测试都是单元测试。 编写测试的简便性和运行它们的速度意味着工程师每天要运行数千个单元测试。

可维护性的重要性
这个场景有两个关键问题:
(1) 单元测试很脆弱。 它们因无害且无关的更改而中断,该更改没有引入真正的错误。
(2) 单元测试不明确。 很难理解如何修复测试,因为一开始就不清楚测试在做什么。
当代码及其测试有多个贡献者时,这种情况很容易发生(现实生活中的软件项目往往会有很多人同时参与其中)。

争取不变的考验
防止脆弱测试的关键策略是努力编写不需要更改的测试,除非项目的
需求变更:
• 内部重构不应改变测试。
• 新功能应不影响现有功能。
• 错误修复不应要求更新测试。
• 行为改变:这些可能需要改变测试。

Testing Implementation:
在这里插入图片描述
Verifies implementation using package-private method

Testing Behaviour:
在这里插入图片描述
This test is using the public API, to the extent of almost
playing a game of Connect4.
The resulting behaviour (a change to the board) is checked using a public method

防止脆性测试
1 仅通过调用公共方法(public methods )进行测试。
2 核实结果是什么,而不是如何实现的。
通过以下方式争取不变的测试:
如果您专注于测试实现而不是行为,您将得到脆弱的测试。
所以总是喜欢针对行为进行测试。

编写清晰的单元测试:

Hamcrest 是一个用于在 Java 中编写富有表现力和可读性的断言的库。 它提供了一组匹配器对象,可以与 JUnit 或 TestNG 等测试框架一起使用,以创建更具描述性和灵活性的断言。

Hamcrest assertions 通过允许您以更流畅和自然的方式构建断言来增强测试的可读性。 您可以使用 Hamcrest 匹配器创建自定义断言,以清晰简洁的方式表达预期行为,而不是仅仅依赖测试框架提供的默认断言方法。

以下是 Hamcrest 断言的一些主要特性和优势:

  1. 流畅易读的语法: Hamcrest 断言使用流畅易读的语法,这使您可以编写非常类似于普通英语语句的断言。 这使得更容易理解断言的意图。

  2. 可扩展和可定制: Hamcrest 提供了一组丰富的内置匹配器,涵盖常见断言,如相等性、可空性、数字比较、集合内容等。 此外,它还允许您创建自定义匹配器来处理内置匹配器未涵盖的特定断言。

  3. 可组合性: Hamcrest 匹配器可以使用“and”、“or”和“not”等逻辑运算符进行组合和组合,使您能够从更简单的断言创建复杂的断言。 这允许更灵活和细粒度的断言。

  4. 诊断消息: Hamcrest 在断言失败时提供详细的诊断消息。 这些消息提供有关预期值和实际值的信息,有助于快速识别断言失败的原因。

下面是将 Hamcrest 断言与 JUnit 结合使用的示例:

导入 org.junit.jupiter.api.Test;
导入静态 org.hamcrest.MatcherAssert.assertThat;
导入静态 org.hamcrest.Matchers.*;公开课 MyTest {@测试public void testStringLength() {String text = "你好,世界!";assertThat(文本,是(notNullValue()));assertThat(text, containsString("你好"));assertThat(文本,hasLength(13));assertThat(文本, anyOf(startsWith("H"), endsWith("!")));}
}

在此示例中,Hamcrest 匹配器用于对字符串执行各种断言。 assertThat 方法用于将匹配器应用于被测试的实际值(text)。 与默认的 JUnit 断言相比,匹配器(iscontainsStringhasLengthanyOf)提供了更具表现力和描述性的断言。

通过使用 Hamcrest 断言,您可以编写更具可读性和表达力的测试,从而更容易理解预期行为并提高测试代码的整体质量。

另一个示例:
在这里插入图片描述

实际结果和预期结果之间的关系由匹配器指定,在本例中为 equalTo。

Hamcrest 匹配器
Hamcrest 有很多“匹配器”,比如 equalTo。
他们可以帮助编写涉及多种类型的断言,包括:
• 字符串——例如,可以检查字符串是否包含子字符串、忽略大小写等。
• 集合——元素是否在集合中; 集合包含什么,忽略顺序等。
如果没有合适的匹配器,很容易编写自己的匹配器。
请参阅 https://www.baeldung.com/java-junit-hamcrest-guide

使您的测试完整而简洁
确保测试包含读者了解它如何得出结果所需的所有信息。
确保它不包含其他不相关和分散注意力的信息。
当测试用例的主体包含读者理解它如何得出结果所需的所有信息时,测试用例就完成了。

当这两个测试用例的主体包含读者需要了解其如何得出结果的所有信息时,这两个测试用例就完成了。
在这里插入图片描述
在这里插入图片描述
枚举所有的动作使得方法更长并且防止将移动序列重新用作辅助方法,但更清楚发生了什么。 棋盘上增加了两列垂直棋子,红色在第 0 列获胜

不要DRY测试
DRY——不要重复自己:工程师需要更新一段代码而不是跟踪所有实例。
缺点:可以使代码不那么清晰,需要遵循引用链。
为了使代码更易于使用,这可能是一个很小的代价……但是成本/收益分析在测试中的表现不同:
• 我们希望测试在软件更改时中断
• 生产代码具有测试套件的优势,可确保在事情变得复杂时它仍能正常工作。 测试应该独立存在!(当测试需要测试时出了问题)

湿而不干(DAMP not DRY)
DAMP:描述性的和有意义的短语
DAMP 不能替代 DRY——它是补充。
“助手”方法可以通过使测试更简洁来帮助使测试更清晰——分解出重复的步骤,这些步骤的细节与被测试的行为无关。
但是重构应该着眼于使测试更具可读性和描述性,而不仅仅是为了减少重复。
不要包括清晰和简洁。

当测试用例不包含其他分散注意力或不相关的信息时,它就是简洁的。
在这里插入图片描述
我们的测试现在包括很多不需要的动作在测试场景并使电路板更难可视化以及测试结果应该是什么。

不要测试方法——测试行为
但是一个方法可能有不止一种行为和/或一些需要更多测试的棘手的极端情况。
例如,makeMove 可以有多种行为,具体取决于棋盘的状态。
对该方法的一次测试没有任何意义,并且可能不是很清楚也不简洁。
更好的方法:为每个行为编写测试。

测试行为
行为是系统在特定状态下如何响应一系列输入的保证。
行为可以表示为“给定 X,当 Y,然后 Z”
例如:
给定一个 Connect4 棋盘,RED 首先开始,当 RED 下了一个棋子后,接下来就轮到 YELLOW 了。

编写行为驱动的测试
行为驱动的测试更倾向于阅读自然语言,因此相应地构建它们
在这里插入图片描述
在被测试的行为之后命名测试.
一个好的名称描述了正在测试的动作(“何时”)和预期结果(“然后”),有时还描述了状态(“给定”)。
一个好的技巧是以“应该”开头的名称,例如
shouldInitializeCorrectly
shouldChangePieceAfterTurn
shouldEndGameWithWinnerWhenFourInARowHorizontally etc.

不要把逻辑放在测试中
不要在测试或逻辑操作中放置条件或循环。
测试应该读作简单的事实陈述,而不是同样需要测试的代码块!
在这里插入图片描述
最好只初始化一个较小的 2x2 板并明确检查每个位置

Making Your Unit Tests Clear
1 Make your tests concise and complete (DAMP and not too DRY!)
2 Don’t structure tests around methods – instead structure around behaviours
3 Use the Given-When-Then pattern for testing behaviour
4 Name Tests after the Behaviour Being Tested
5 Don’t put logic in tests

相关文章:

java单元测试( Hamcrest 断言)

java单元测试( Hamcrest 断言) 单元测试特征: 1 范围狭窄 2 限于单一类或方法 3 体积小 为什么要编写单元测试? 为了防止错误(很明显!) 而且还可以提高开发人员的生产力,因为单元测试: (1) 帮助实施——在…...

讨论和总结 树模型 的三种序列化 方式的区别(模型存储大小、序列化所用内存、序列化速度)...

一、前言 本文总结常用树模型: rf,xgboost,catboost和lightgbm等模型的保存和加载(序列化和反序列化)的多种方式,并对多种方式从运行内存的使用和存储大小做对比 二、模型 2.1 安装环境 pip install xgboos…...

Halcon中的一些3D算子

一、记录一些Halcon里的关于3D的算子 1.read_object_model_3d 从文件读取一个3d模型 如下图,读的一个ply文件出来是个3d点云模型 2.visualize_object_model_3d 交互式展示3d模型 即上个算子读出来后,通过这个算子可以把3d模型显示出来旋转、平移&am…...

Android:Selector + Layer-lists 实现 AppCompatCheckBox

最近做项目涉及到一些UI相关的东东,虽然比较简单,但是也很有趣,写两篇简短的博客记录一下。 一."Selector 两张图片"实现 AppCompatCheckBox AppCompatCheckBox 是 androidx的一个widget:androidx.appcompat.widget.…...

TreeMap类型添加数据

package com.test.Test11;import java.util.*;public class Test02 {public static void main(String[] args) {/** 增加:put(K key,V value)* 删除:clear() remove(Object key)* 修改:* 查看:entrySet() get(Object key) keySet(…...

iOS 16 UI 设计系统免费在线使用方法

1、iOS 16 UI 设计系统中有什么? iOS 16 UI 设计系统通常包含以下组件和元素: 1. 按钮:包括操作按钮、图标按钮、导航按钮、滚动按钮、切换按钮、单选按钮、复选框按钮、呼叫按钮等各种类型的按钮。 2. 窗口和 UI 控件:包括标签…...

【接口测试】JMeter接口关联测试

‍‍1 前言 我们来学习接口管理测试,这就要使用到JMeter提供的JSON提取器和正则表达式提取器了,下面我们来看看是如何使用的吧。 2 JSON提取器 1、添加JSON提取器 在线程组右键 > 添加 > 后置处理器 > JSON提取器 2、JSON提取器参数说明 N…...

腾讯云服务器ping不通解决方法(公网IP/安全组/系统多维度)

腾讯云服务器ping不通什么原因?ping不通公网IP地址还是域名?新手站长从云服务器公网IP、安全组、Linux系统和Windows操作系统多方面来详细说明腾讯云服务器ping不通的解决方法: 目录 腾讯云服务器ping不通原因分析及解决方法 安全组ICMP协…...

【C++/嵌入式笔试面试八股】一、32.封装

封装 08.C++中struct和class的区别🍊 相同点 两者都拥有成员函数、公有和私有部分任何可以使用class完成的工作,同样可以使用struct完成不同点 两者中如果不对成员不指定公私有,struct默认是公有的,class则默认是私有的class默认是private继承, 而struct默认是public继…...

【算法】Transform to Chessboard 变为棋盘

文章目录 Transform to Chessboard 变为棋盘问题描述:分析代码 Transform to Chessboard 变为棋盘 问题描述: 一个 n x n 的二维网络 board 仅由 0 和 1 组成 。每次移动,你能任意交换两列或是两行的位置。 返回 将这个矩阵变为 棋盘 所需…...

vue通过封装$on定义全局事件

我们先在vue项目的src跟目录下创建一个文件夹 叫 utils 下面创建一个js文件夹 叫 bus.js 参考代码如下 import Vue from "vue"; export default new Vue();然后 我们就可以来用了 在需要定义事件的组件中编写 <template><div><h1>Hello world!&…...

资产管理规范

生产系统资产管理规范 1. 引言 生产系统的资产管理是确保生产系统正常运行和提高生产效率的关键因素之一。本文档旨在制定一套规范&#xff0c;以确保生产系统中的资产&#xff0c;包括服务器和软件等&#xff0c;得到有效管理和保护。 2. 资产分类 生产系统资产可根据其性质…...

已解决:如何从别人的仓库那里克隆到自己的仓库,并修改代码并提交。

一、场景 拉取项目代码后&#xff0c;如果要共同开发一个项目的自动化代码&#xff0c;此时需要把自己写的代码部分提交到代码仓库。 可以用pycharm把修改的代码push到代码仓库 二、操作方法 1.从别人的仓库那里点击fork&#xff0c;将仓库克隆到自己的仓库。 2.在pychar…...

剑指 Offer 18. 删除链表的节点

&#x1f680; 作者简介&#xff1a;一名在后端领域学习&#xff0c;并渴望能够学有所成的追梦人。 &#x1f681; 个人主页&#xff1a;不 良 &#x1f525; 系列专栏&#xff1a;&#x1f6f8;剑指 Offer &#x1f4d5; 学习格言&#xff1a;博观而约取&#xff0c;厚积而薄…...

WiFi 6 vs WiFi 5

在现代无线通信领域&#xff0c;WiFi已经成为人们日常生活中不可或缺的一部分。随着技术的不断发展&#xff0c;WiFi标准也在不断更新和演进。WiFi 6&#xff08;802.11ax&#xff09;和WiFi 5&#xff08;802.11ac&#xff09;是当前两个主要的WiFi标准。 本文将详细介绍WiFi …...

PHP语言基础

一.标记风格 标记风格分为四类(推荐XML) 1.XML风格 <?php echo这是xml风格‘&#xff1b; ?> 注意&#xff1a;结束标识符必须单独另起一行&#xff0c;并且不能有空格。在标识符前后有其他符号或者字符也会发生错误。 2.脚本风格 <script languagephp> …...

怎么用Excel VBA写一个excel批量合并的程序?

您可以按照以下VBA代码来实现把同一路径上的所有工作簿合并到同一个工作簿中&#xff1a; VBA Option Explicit Sub MergeWorkbooks() Dim path As String, fileName As String, sheet As Worksheet Dim targetWorkbook As Workbook, sourceWorkbook As Workbook Dim workshe…...

WuThreat身份安全云-TVD每日漏洞情报-2023-05-22

漏洞名称:Apple WebKit 任意代码执行漏洞 漏洞级别:中危 漏洞编号:CVE-2023-32373 相关涉及:Apple iOS和iPadOS 16.4.1 漏洞状态:在野 参考链接:https://tvd.wuthreat.com/#/listDetail?TVD_IDTVD-2023-12579 漏洞名称:海康威视部分iVMS系统存在文件上传漏洞 漏洞级别:未定义…...

Eclipse教程 Ⅵ

今天分享Eclipse Java 构建路径、Eclipse 运行配置(Run Configuration)和Eclipse 运行程序 Eclipse Java 构建路径 设置 Java 构建路径 Java构建路径用于在编译Java项目时找到依赖的类&#xff0c;包括以下几项&#xff1a; 源码包项目相关的 jar 包及类文件项目引用的的类…...

Seaborn.load_dataset()加载数据集失败最佳解决方法

load_dataset() 是 Seaborn 库中提供的一个函数&#xff0c;用于加载一些原始数据集。这些数据集包含了许多经典的数据集&#xff0c;比如鸢尾花数据集、小费数据集等&#xff0c;这些数据集在数据可视化和机器学习中非常常见。 使用 load_dataset() 函数可以方便地获取这些数…...

React Native 开发环境搭建(全平台详解)

React Native 开发环境搭建&#xff08;全平台详解&#xff09; 在开始使用 React Native 开发移动应用之前&#xff0c;正确设置开发环境是至关重要的一步。本文将为你提供一份全面的指南&#xff0c;涵盖 macOS 和 Windows 平台的配置步骤&#xff0c;如何在 Android 和 iOS…...

EtherNet/IP转DeviceNet协议网关详解

一&#xff0c;设备主要功能 疆鸿智能JH-DVN-EIP本产品是自主研发的一款EtherNet/IP从站功能的通讯网关。该产品主要功能是连接DeviceNet总线和EtherNet/IP网络&#xff0c;本网关连接到EtherNet/IP总线中做为从站使用&#xff0c;连接到DeviceNet总线中做为从站使用。 在自动…...

优选算法第十二讲:队列 + 宽搜 优先级队列

优选算法第十二讲&#xff1a;队列 宽搜 && 优先级队列 1.N叉树的层序遍历2.二叉树的锯齿型层序遍历3.二叉树最大宽度4.在每个树行中找最大值5.优先级队列 -- 最后一块石头的重量6.数据流中的第K大元素7.前K个高频单词8.数据流的中位数 1.N叉树的层序遍历 2.二叉树的锯…...

DeepSeek 技术赋能无人农场协同作业:用 AI 重构农田管理 “神经网”

目录 一、引言二、DeepSeek 技术大揭秘2.1 核心架构解析2.2 关键技术剖析 三、智能农业无人农场协同作业现状3.1 发展现状概述3.2 协同作业模式介绍 四、DeepSeek 的 “农场奇妙游”4.1 数据处理与分析4.2 作物生长监测与预测4.3 病虫害防治4.4 农机协同作业调度 五、实际案例大…...

重启Eureka集群中的节点,对已经注册的服务有什么影响

先看答案&#xff0c;如果正确地操作&#xff0c;重启Eureka集群中的节点&#xff0c;对已经注册的服务影响非常小&#xff0c;甚至可以做到无感知。 但如果操作不当&#xff0c;可能会引发短暂的服务发现问题。 下面我们从Eureka的核心工作原理来详细分析这个问题。 Eureka的…...

AirSim/Cosys-AirSim 游戏开发(四)外部固定位置监控相机

这个博客介绍了如何通过 settings.json 文件添加一个无人机外的 固定位置监控相机&#xff0c;因为在使用过程中发现 Airsim 对外部监控相机的描述模糊&#xff0c;而 Cosys-Airsim 在官方文档中没有提供外部监控相机设置&#xff0c;最后在源码示例中找到了&#xff0c;所以感…...

虚拟电厂发展三大趋势:市场化、技术主导、车网互联

市场化&#xff1a;从政策驱动到多元盈利 政策全面赋能 2025年4月&#xff0c;国家发改委、能源局发布《关于加快推进虚拟电厂发展的指导意见》&#xff0c;首次明确虚拟电厂为“独立市场主体”&#xff0c;提出硬性目标&#xff1a;2027年全国调节能力≥2000万千瓦&#xff0…...

三分算法与DeepSeek辅助证明是单峰函数

前置 单峰函数有唯一的最大值&#xff0c;最大值左侧的数值严格单调递增&#xff0c;最大值右侧的数值严格单调递减。 单谷函数有唯一的最小值&#xff0c;最小值左侧的数值严格单调递减&#xff0c;最小值右侧的数值严格单调递增。 三分的本质 三分和二分一样都是通过不断缩…...

宇树科技,改名了!

提到国内具身智能和机器人领域的代表企业&#xff0c;那宇树科技&#xff08;Unitree&#xff09;必须名列其榜。 最近&#xff0c;宇树科技的一项新变动消息在业界引发了不少关注和讨论&#xff0c;即&#xff1a; 宇树向其合作伙伴发布了一封公司名称变更函称&#xff0c;因…...

篇章二 论坛系统——系统设计

目录 2.系统设计 2.1 技术选型 2.2 设计数据库结构 2.2.1 数据库实体 1. 数据库设计 1.1 数据库名: forum db 1.2 表的设计 1.3 编写SQL 2.系统设计 2.1 技术选型 2.2 设计数据库结构 2.2.1 数据库实体 通过需求分析获得概念类并结合业务实现过程中的技术需要&#x…...