Fork me on GitHub

Python基础—断言(assert)


环境及版本

1
2
3
Windows 10 x64
Python 2.7
Pycharm 4.5.1

什么是断言

assert和if语句类似,是用来检查一个条件,但不同的是如果它为真,就不做任何事。如果它为假,则会抛出AssertError异常。

1
2
3
4
5
6
7
8
9
a = 10
assert a > 0, 'a > 0'
assert a < 20, 'a < 20'
assert a%2 != 0, 'a is not an even number'

Traceback (most recent call last):
File "D:/pythonlearning/assertlearning/assert_test.py", line 9, in <module>
assert a%2 != 0, 'a is not an even number'
AssertionError: a is not an even number

什么时候使用断言

在Stack Overflow上有个问题:Best practice for Python Assert
【节选一些回答】

Asserts should be used to test conditions that should never happen. The purpose is to crash early in the case of a corrupt program state.

Exceptions should be used for errors that can conceivably happen, and you should almost always create your own Exception classes.
——Deestan

  • 简单翻译一下就是(英语不好见谅):
  • 断言应该使用在某种情况几乎不会发生的条件下(它是为了确保代码的正确性),目的是为了保证这种小概率事件发生时能尽早终止程序
  • 异常应该使用在某些问题预见性的会出现,并且你可以创建自己的异常类

  • 总的来说断言的作用不是用来检查代码的逻辑性错误,所以应该区分断言和异常,不能将需要捕获异常的地方用断言代替
  • 如果你能保证你的代码某部分是正确的,则这个部分就无需用断言,因为即使用了也不会触发

断言做单元测试

  • 在代码中利用断言做小的单元测试是可以的
  • 比如测试某个函数的执行是否正确
1
2
3
4
5
6
7
8
9
def assert_test(a,b):
return a + b
assert 3 == assert_test(1,2), 'right'
assert 3 == assert_test(1,4), 'error'

Traceback (most recent call last):
File "D://pythonlearning/assertlearning/assert_test.py", line 16, in <module>
assert 3 == assert_test(1,4), 'error'
AssertionError: error

断言做防御型编程

  • 不是让你的代码防御现在的错误,而是防止在代码修改后引发的错误
  • 比如现在的代码是良好的,但是随着开发的继续,可能某些函数、依赖关系发生变化,可能会导致错误的出现
  • 在这种情况下,可以利用断言使代码发生不兼容的变化时立刻发生错误,防御型编程能帮助人们今早的发现bug

不要用断言的场景

  • 不要用它测试用户提供的数据
  • 不要用断言来检查你觉得在你的程序的常规使用时会出错的地方。断言是用来检查非常罕见的问题。
  • 有的情况下,不用断言是因为它比精确的检查要短,它不应该是懒码农的偷懒方式
  • 不要用它来检查对公共库的输入参数,因为它不能控制调用者,所以不能保证调用者会不会打破双方的约定
  • 不要为你觉得可以恢复的错误用断言。换句话说,不用改在产品代码里捕捉到断言错误
  • 不要用太多断言以至于让代码很晦涩

参考:[1]StackOverflow—Best practice for Python Assert、[2]伯乐在线—Python中何时使用断言


转载请注明出处


Thank you for your support.