原创翻译-测试驱动开发(TDD)
测试驱动开发原则 翻译自<<Expert Python Programming>>
测试驱动开发是指首先编写包含所有测试软件特点的测试集,然后再去开发软件。也就是说,在编写软件之前先把这个软件的测试文档写清楚。举个例子,如果有个程序员想编写一个可以计算一组数字平均值的函数,那我们先要写出这个函数是怎么用的。我们可以这样写:
assert average(1, 2, 3) == 2
assert average(1, -3) == -1
这些测试例子也可以由别的人来负责编写。现在,这个函数如果通过了这两个测试那么就可以拿出去用了:
>>> def average(*numbers):
... return sum(numbers) / len(numbers)
...
>>> assert average(1, 2, 3) == 2
>>> assert average(1, -3) == -1
但是我们新增的测试实例却发现了一个错误:
>>> assert average(0, 1) == 0.5
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AssertionError
我们可以根据这个错误来对代码进行修改:
>>> def average(*numbers):
... # makes sure all numbers can be used as floats
... numbers = [float(number) for number in numbers]
... return sum(numbers) / float(len(numbers))
...
>>> assert average(0, 1) == 0.5
并且我们还可增加更多的测试实例:
>>> try:
... average()
... except TypeError:
... # we want an empty sequence to throw a type error
... pass
...
Traceback (most recent call last):
File "<stdin>", line 2, in <module>
File "<stdin>", line 3, in average
ZeroDivisionError: integer division or modulo by zero
>>>
>>> def average(*numbers):
... if numbers == ():
... raise TypeError(('You need to provide at '
... 'least one number'))
... numbers = [float(number) for number in numbers]
... return sum(numbers) / len(numbers)
...
>>> try:
... average()
... except TypeError:
... pass
...
这里我们可以编写一个测试函数,函数里面包含了我们要使用的所有测试,每次修改我们的代码后就可以运行着个函数:
>>> def test_average():
... assert average(1, 2, 3) == 2
... assert average(1, -3) == -1
... assert average(0, 1) == 0.5
... try:
... average()
... except TypeError:
... pass
...
>>> test_average()
每次我们修改代码之后,我们也会相应的在test_average里面增加新的测试集。同时我们也要保证之前的测试集可以通过。最好的办法是我们把对应模块的所有测试集都放在一个文件夹下面,每个模块对应一个测试文件夹。驱动测试开发可以为我们带来这些好处:
- 防止代码回归
- 提高代码质量
- 提供最简便的文档
- 快速的创造健壮代码
防止代码回归
身为程序员,我们都碰到过软件回归这类问题。软件回归是指我们在对代码的修改过程中导致了其它的错误。这类问题发生通常是因为我们对当前代码作出的改动所带来的影响不够清楚。对这里代码的小小改动有可能影响了其它功能的使用,而且有时候可能导致非常严重的后果,比方说直接毁坏了当前的数据。
为了避免这类事情的发生,我们应该在每一次修改代码之后都去测试把这个软件的所有测试集合都来测试一遍。
如果是同时有几个人在对代码进行修改的话可能使得这类问题更加的严重,因为每个人都不会完全明白软件的每个部分是干什么的。虽然版本控制系统防止了这类冲突的发生,但并不意味着他能防止这次代码修改所造成的潜在问题。
测试驱动开发能够帮助减少软件回归这类问题。在每一次代码修改过后我们都会自动的对软件进行所有的测试。但前提是我们有一个正确的开发软件测试集。当我们使用测试驱动开发的时候,我们的测试集会随着我们代码的改变而增加。
提高代码质量
当我们编写了一个新的模块,类或者函数的时候,程序员大多都只关注自己的代码如何才能更加高效的运转。但当他们在考虑这些的时候,他们很可能会忽略了一点:他们现在编写的这个函数是何时何地怎样去使用的?是不是所有的参数都是方便使用而且符合逻辑的?它命名的API名称是否符合规范?
解决这一问题的唯一方法就是撰写使用规范。
提供最好的开发文档
对开发者而言测试文档是最能够说明软件是如何工作的东西。它们告诉了开发者这个软件如何使用。通过阅读这些测试文档开发者可以快速而且深入的了解这些代码的功效。有时一个例子胜过千言万语。更重要的是这些测试文档从来都是和代码同步的,我们不用再去编写一个介绍文档,而且在每次代码进行修改时还不能忘了去更新它。
编写更加健壮的代码
如果没有测试集,那么软件的开发将会导致很多额外的错误。一个错误发现之后,可能引起这个错误的地方和发现这个错误的地方相差十万八千里。你都不知道该去找谁,然后你就只能自己不知道花上多少时间来解决这个问题。如果我们采用测试驱动开发,当我们测试出现错误的时候我们的错误只会限定在一个很小的地方,这个时候对代码进行修改不仅对程序员更加容易,而且对身心也更加健康。。
如果你算一算开发一个软件所用的时间,通常情况下测试驱动开发总是最快的。
但是测试驱动开发也有时候会出现问题,有时候我们在编写测试文档时候,对环境的配置并不总是那么容易的,比方说我们的代码和LDAP或者SQL服务器进行交互的时候,写一篇测试文档可能是一个非常困难的事情。
原创翻译-测试驱动开发(TDD)的更多相关文章
- 测试驱动开发(TDD)的思考
极限编程 敏捷开发是一种思想,极限编程也是一种思想,它与敏捷开发某些目标是一致的.只是实现方式不同.测试驱动开发是极限编程的一部分. 1.极限编程这个思路的来源 Kent Beck先生最早在其极限编程 ...
- 测试驱动开发 TDD
一.详解TDD 1.1.TDD概念 :Test Drived Develop 测试驱动开发是敏捷开发中的一项核心实践和技术,也是一种方法论.TDD的原理是在开发功能代码之前,编写单元测试用例代码,测试 ...
- 测试驱动开发(TDD)及测试框架Mocha.js入门学习
组里马上要转变开发模式,由传统的开发模式(Developer开发,QA测试),转变为尝试TDD(Test-driven development,测试驱动开发)的开发模型.由此将不存在QA的角色,或者仅 ...
- 44 | 测试先行:测试驱动开发(TDD)
- 浅谈测试驱动开发(TDD)
测试驱动开发(TDD)是极限编程的重要特点,它以不断的测试推动代码的开发,既简化了代码,又保证了软件质量.本文从开发人员使用的角度,介绍了 TDD 优势.原理.过程.原则.测试技术.Tips 等方面. ...
- (转)浅谈测试驱动开发(TDD)
测试驱动开发(TDD)是极限编程的重要特点,它以不断的测试推动代码的开发,既简化了代码,又保证了软件质量.本文从开发人员使用的角度,介绍了 TDD 优势.原理.过程.原则.测试技术.Tips 等方面. ...
- 敏捷开发 —— TDD(测试驱动开发)
测试驱动开发 TDD(Test-Driven Development)是敏捷开发的一项核心实践,同时也是一种设计技术和方法. 既然是测试驱动,便是测试,测试用例先行: 首先编写好测试用例,期待值,实际 ...
- 测试驱动开发与Python
最近在看一本书<Test-Driven Development with Python>,里面非常详细的介绍了如何一步一步通过测试驱动开发(TDD)的方式开发Web项目.刚好这本书中使用了 ...
- 基于Python的测试驱动开发实战
近年来测试驱动开发(TDD)受到越来越多的关注.这是一个持续改进的过程,能从一开始就形成规范,帮助提高代码质量.这是切实可行的而非天马行空的. TDD的全过程是非常简单的.借助TDD,代码质量会得到提 ...
随机推荐
- [moka同学摘录]iptables防火墙规则的添加、删除、修改、保存
文章来源:http://www.splaybow.com/post/iptables-rule-add-delete-modify-save.html 本文介绍iptables这个Linux下最强大的 ...
- python pip 升级每个包
pip本身不自带升级所有包的功能, 但可以通过下面的脚本实现. import pip from subprocess import call for dist in pip.get_installed ...
- Angularjs,WebAPI 搭建一个简易权限管理系统 —— WebAPI项目主体结构(四)
目录 前言 Angularjs名词与概念 Angularjs 基本功能演示 系统业务与实现 WebAPI项目主体结构 Angularjs 前端主体结构 5.0 WebAPI项目主体结构 5.1 总体结 ...
- [js开源组件开发]图片放大镜
图片放大镜 一般情况下,手机由于屏幕太小,会有图片上看不清的问题,所以我就做了一个放大镜的js效果,支持pc和移动端.它的原理是利用的backgroundsize来实现的,所以你的浏览器首先要支持这个 ...
- CSS 属性 - 伪类和伪元素的区别
伪类和伪元素皆独立于文档结构.它们获取元素的途径也不是基于id.class.属性这些基础的元素特征,而是在处于特殊状态的元素(伪类),或者是元素中特别的内容(伪元素).区别总结如下: ①写法不一样: ...
- VS2010运行正常的控制台程序在VS2015中出现乱码的解决方法
以前在Visual Stuido 2010中运行正常的控制台程序,在Visual Studio 2015中出现乱码,找到<Visual Studio 2015的坑:中文字符串编译后成乱码> ...
- 【读书笔记】iOS-Tagged Pointer对象-注意事项
一,2013年9月,苹果推出了iPhone5s,与此同时,iPhone5s配备了首个采用64位架构的A7双核处理器,为了节省内存和提高执行效率,苹果提出了Tagged Pointer的概念. 对于64 ...
- iOS OC内联函数 inline的详解
inline 在iOS中的一些框架中,static inline是经常出现的关键字组合. static自不用多说,表示在当前文件中应用,如 static A, 在其它文件中也可以出现static A. ...
- C++中派生类对象的内存布局
主要从三个方面来讲: 1 单一继承 2 多重继承 3 虚拟继承 1 单一继承 (1)派生类完全拥有基类的内存布局,并保证其完整性. 派生类可以看作是完整的基类的Object再加上派生类自己的Objec ...
- centos性能监控系列三:监控工具atop详解
引言 Linux以其稳定性,越来越多地被用作服务器的操作系统(当然,有人会较真地说一句:Linux只是操作系统内核:).但使用了Linux作为底层的操作系统,是否我们就能保证我们的服务做到7*24地稳 ...