zl程序教程

您现在的位置是:首页 >  其他

当前栏目

预处理功能调试 assert和NDEBUG

调试预处理 功能 assert
2023-09-27 14:27:31 时间

头文件#include <cassert>
assert是一种预处理宏(preprocessor macro),使用一个表达式作为其条件。

assert(expr);

assert有一点像是关卡,检查每个途径这个关卡的程序流的身份(expr),守城的人拿起来你的ID一看,满足就放行,不满足则报警终止程序运行。默认情况下,assert启用,你可以通过以下两种情况使其失效:

  • 编译时通过-D传递NDEBUG宏
  • 源文件#define 定义NDEBUG宏

总的来说,assert应该用在确实不可能发生的情况,仅用于调试,不用于代替运行时逻辑检查。当然NDEBUG宏还可以用于定义调试时才运行的代码:

#ifndef NDEBUG
	//有点绕,如果没有定义不调试,那就是调试
	//我想要在调试时执行的代码
#endif

在没有定义不调试(也就是调试)时,我们可以打印一些信息:__func__ __FILE__ __TIME__ __DATE__(不用数了是双下划线)。可以通过cerr输出这些字面值常量。

他人提供的assert使用经验:

  • 在函数开始处检验传入参数的合法性
  • 每个assert只检验一个条件,因为同时检验多个条件时,如果断言失败,无法直观的判断是哪个条件失败
  • 不能使用改变环境的语句,因为assert只在DEBUG个生效,如果这么做,会使用程序在真正运行时遇到问题 错误: assert(i++ < 100):
  • assert和后面的语句应空一行,以形成逻辑和视觉上的一致感

用断言的几个原则:

  • 使用断言捕捉不应该发生的非法情况。不要混淆非法情况与错误情况之间的区别,后者是必然存在的并且是一定要作出处理的。
  • 使用断言对函数的参数进行确认。
  • 当进行防错性编程时,如果"不可能发生"的事情的确发生了,则要使用断言进行报警。

[1] https://www.runoob.com/w3cnote/c-assert.html