以前编写程序从没有做过单元测试的工作,所以在后期会花很多时间去纠错,这也就是软件工程中的2:8定律。最近要完成一个项目,要求要对系统中的主类和主函数作出单元测试的保证,才去查找了相关方面的资料,看过后觉得单元测试在工程中是必不可少的一项,下面就对有关C++的单元测试做一个简单的介绍,因为本人还没有系统的去理解相关方面的内容,所以只是介绍一些简单的应用和浅显的原理,有不到之处还请指出:

1) 什么是单元测试

单元测试(unit test,模块测试又称白盒测试)是开发者编写的一小段代码,用于检测被测代码的一个很小的,很明确的功能是否正确,通过编写单元测试可以在编码阶段发现程序编码错误,甚至是程序设计错误。现在回想下我们平时编程的过程:梳理逻辑->编写代码->调bug的一个循环过程;其中调试bug是一个很耗费时间的过程,而且调完一堆bug后我们对自己程序的信任度却在不断降低,因为不知道还会不会出bug。这是因为我们所调试的bug只是当前出现的,没有出现的呢,我们就说不好了。我们知道程序中一个简单的if...else...语句都会对数据流有一次分类,不同类的数据流所对应的操作不同,想想这些你就会觉得自己的代码还不知道要出多少bug。单元测试却很好的解决了这个问题,你要做的就是对核心的函数,核心的逻辑,将所有可能的数据流都列出来,进行一次全覆盖测试,这样你代码的健壮性就会很强。

2)如何写单元测试

最简单的方法那就是自己将核心的函数抽出来,重新建立一个项目,提供所有可能的数据流入口,对函数进行测试。这样做有两个缺陷:1、只能处理一些简单的项目,对于逻辑较为复杂,数据分支较多的就无法操作了;2、没有一个很好的框架,写出的代码没有一个统一的规则,可读性不强;为此,依托一个现有的测试框架是必不可少的。CppUnit是xunit家族的一员,xunit是一种测试框架,最早是在smalltalk上实现,后来被广泛的在各种语言上实现,除了Cppunit还有NUnit(c#版本)phpunit(php版本)和CppUnit相似的gtest(google的C++测试工具,据说在应用上要优于CppUnit,没有用过,大家可以试试),cmockery(c语言测试工具,也是google的)。cppunit以源码的方式发布,所以想要使用这个工具就要自己下载编译(后面会介绍到),同时在windows下CppUnit还带了一个MFC项目,可以以图形界面的方式报告编译情况。

3)如何编译CppUnit

我的编译环境是win7,vs2010;

1 :下载源码包 最新的版本是1.21.1(2008年最后一次更新)

地址 :http://sourceforge.net/projects/cppunit/ 或者直接点击 http://sourceforge.net/projects/cppunit/files/cppunit/1.12.1/cppunit-1.12.1.tar.gz/download

2 : 复制cppunt-1.12.1到c:\解压得到目录C:\cppunit-1.12.1

3 : 进入C:\cppunit-1.12.1\src 用VS2010打开CppUnitLibraries.dsw提示转换,转换之

4 : 在项目列表看见一堆项目,默认是以Debug的方式编译,如以该方式编译需要修改目标文件名

cppunit                $(ProjectName)   ->   $(ProjectName)d
cppunit_dll           $(ProjectName)   ->   cppunitd_dll
DllPlugInTester     $(ProjectName)   ->   $(ProjectName)d_dll
TestPlugInRunner $(ProjectName)   ->   $(ProjectName)d
TestRunner          $(ProjectName)  ->   $(ProjectName)d

需要修改目标文件名的原因是上述项目都设置了生成事件,在生成以后都会把生成的文件复制到lib目录下,个人判断d应该是代表了测试版的意思,如果是Release版本生成的目标文件都是项目名不需要修改

5 : 修改DSPlugIn入口
属性,配置属性,链接器,高级,无入口点 设置是

6 : 修改无法加载类型库(编译TestPlugInRunner,TestRunner)会报错其中7.0修改为8.0
#import "libid:80cc9f66-e7d8-4ddd-85b6-d9e6cd0e93e2" version("7.0") lcid("0") raw_interfaces_only named_guids

以上设置都全做完以后就可以整体编译解决方案了(这里要注意一点,要将上述所有的配置实现后再编译,不要对每个项目进行单独编译;否则会出现诸如“该文件没有一个关联的程序...”这样的问题)

4)如何用Cppunit

先写一个测试的Demo,初步体验下Cppunit的用法

1、打开vs2010文件项, 新建VC++空项目:cppUnitTest

2、 设置环境变量;在系统变量PATH的尾巴上添加“C:\cppunit-1.12.1”(这是我的地址)

3、 [项目cppUnitTest]-[属性]-[配置属性]-[C/C++]-[常规]-[附加包含目录]: "../include"

4、 [项目cppUnitTest]-[属性]-[配置属性]-[链接器]-[常规]-[附加库目录]: "../lib"

5、 [项目cppUnitTest]-[属性]-[配置属性]-[链接器]-[输入]-[附加依赖项]: "cppunitd.lib"

6、新建文件main.cpp

#include <cppunit/TestCase.h>
#include <cppunit/TestResult.h>
#include <cppunit/TestResultCollector.h>
#include <cppunit/TextOutputter.h>
#include <cppunit/TestCaller.h>
#include <cppunit/TestRunner.h> // 定义测试类
class StringTest : public CppUnit::TestFixture
{
public:
void setUp() // 初始化
{
m_str1 = "Hello, world";
m_str2 = "Hi, cppunit";
} void tearDown() // 清理
{
} void testSwap() // 测试方法1
{
std::string str1 = m_str1;
std::string str2 = m_str2;
m_str1.swap(m_str2); CPPUNIT_ASSERT(m_str1 == str2);
CPPUNIT_ASSERT(m_str2 == str1);
} void testFind() // 测试方法2
{
int pos1 = m_str1.find(',');
int pos2 = m_str2.rfind(','); CPPUNIT_ASSERT_EQUAL(, pos1);
CPPUNIT_ASSERT_EQUAL(, pos2);
} protected:
std::string m_str1;
std::string m_str2;
}; int main(int argc, char* argv[])
{
CppUnit::TestResult r;
CppUnit::TestResultCollector rc;
r.addListener(&rc); // 准备好结果收集器 CppUnit::TestRunner runner; // 定义执行实体
runner.addTest(new CppUnit::TestCaller<StringTest>("testSwap", &StringTest::testSwap)); // 构建测试用例1
runner.addTest(new CppUnit::TestCaller<StringTest>("testFind", &StringTest::testFind)); // 构建测试用例2
runner.run(r); // 运行测试 CppUnit::TextOutputter o(&rc, std::cout);
o.write(); // 将结果输出 return rc.wasSuccessful() ? : -;
}

以上代码时使用Cppunit框架对string类的两个函数进行测试,在testFind()中调用string的find函数并通过CPPUNIT_ASSERT对结果进行测试;

C++之单元测试的更多相关文章

  1. Intellij idea添加单元测试工具

    1.idea 版本是14.0.0 ,默认带有Junit,但是不能自动生成单元测试,需要下载JunitGererator2.0插件 2.Settings -Plugins,下载 JunitGenerat ...

  2. Python的单元测试(二)

    title: Python的单元测试(二) date: 2015-03-04 19:08:20 categories: Python tags: [Python,单元测试] --- 在Python的单 ...

  3. Python的单元测试(一)

    title: Python的单元测试(一) author: 青南 date: 2015-02-27 22:50:47 categories: Python tags: [Python,单元测试] -- ...

  4. javascript单元测试框架mochajs详解

    关于单元测试的想法 对于一些比较重要的项目,每次更新代码之后总是要自己测好久,担心一旦上线出了问题影响的服务太多,此时就希望能有一个比较规范的测试流程.在github上看到牛逼的javascript开 ...

  5. 使用NUnit为游戏项目编写高质量单元测试的思考

    0x00 单元测试Pro & Con 最近尝试在我参与的游戏项目中引入TDD(测试驱动开发)的开发模式,因此单元测试便变得十分必要.这篇博客就来聊一聊这段时间的感悟和想法.由于游戏开发和传统软 ...

  6. 我这么玩Web Api(二):数据验证,全局数据验证与单元测试

    目录 一.模型状态 - ModelState 二.数据注解 - Data Annotations 三.自定义数据注解 四.全局数据验证 五.单元测试   一.模型状态 - ModelState 我理解 ...

  7. ABAP单元测试最佳实践

    本文包含了我在开发项目中经历过的实用的ABAP单元测试指导方针.我把它们安排成为问答的风格,欢迎任何人添加更多的Q&A's,以完成这个列表. 在我的项目中,只使用传统的ABAP report. ...

  8. python_单元测试unittest

    Python自带一个单元测试框架是unittest模块,用它来做单元测试,它里面封装好了一些校验返回的结果方法和一些用例执行前的初始化操作. 步骤1:首先引入unittest模块--import un ...

  9. .Net中的AOP系列之《单元测试切面》

    返回<.Net中的AOP>系列学习总目录 本篇目录 使用NUnit编写测试 编写和运行NUnit测试 切面的测试策略 Castle DynamicProxy测试 测试一个拦截器 注入依赖 ...

  10. React单元测试——十八般兵器齐上阵,环境构建篇

    一个完整.优秀的项目往往离不开单元测试的环节,就 github 上的主流前端项目而言,基本都有相应的单元测试模块. 就 React 的项目来说,一套完整的单元测试能在在后续迭代更新中回归错误时候给与警 ...

随机推荐

  1. 理解JMS规范中消息的传输模式和消息持久化

    http://blog.csdn.net/aitangyong/article/category/2175061 http://blog.csdn.net/aitangyong/article/det ...

  2. Linux系统启动过程介绍

    Linux系统启动过程介绍 学习操作系统有必要了解一下系统的启动过程,这样在面对各种系统故障的时候能快速定位解决问题,下面以Centos来分析linux系统的启动过程. 1.BIOS自检:当开机的时候 ...

  3. H.264 RTPpayload 格式------ H.264 视频 RTP 负载格式

    H.264 RTPpayload 格式------ H.264 视频 RTP 负载格式 1. 网络抽象层单元类型 (NALU) NALU 头由一个字节组成, 它的语法如下: +------------ ...

  4. C语言随笔_区分=与==

    写C程序时,经常发现大家=与==分不清.最常见的写法如下:int a = 3;if(a = 1){.......} 写程序的人原意是想如果a等于1的话,就执行花括号里的语句,a初始化时的值是3,也就是 ...

  5. 什么是优先级队列(priority queue)?

    有时候我们需要在某个元素集合中找到最小值和最大值 .优先级队列抽象数据(Priority Queue ADT)模型是我们能够使用的方法之一,这是一种支持插入和删除最小值(DeleteMin)或者最大值 ...

  6. poj 1020 Anniversary Cake(切正方形蛋糕+搜索)

                                                                                                         ...

  7. [置顶] 教你如何搭建RobotFramework环境

    看到这篇文章的朋友,相信已经知道RobotFramework是干什么的了,我这里就不再赘述了. 搭建步骤: 1. 下载安装Python,下载地址http://www.python.org/getit/ ...

  8. tomcat web项目部署方式

    1.利用MyEclipse的部署部工具部署项目,可以直接部署成文件形式,这样当启动tomcat后可以直接访问 2.利用MyEclipse部署工具部署war形式,点击发布选择tomcat时可以选择该项 ...

  9. iOS开发系列--打造自己的“美图秀秀”

    概述 在iOS中可以很容易的开发出绚丽的界面效果,一方面得益于成功系统的设计,另一方面得益于它强大的开发框架.今天我们将围绕iOS中两大图形.图像绘图框架进行介绍:Quartz 2D绘制2D图形和Co ...

  10. Single Number(JAVA)

    Given an array of integers, every element appears twice except for one. Find that single one. Note: ...