在 C++ 中确保条件编译代码的单元测试
Unit test for ensuring conditionally compiled code in c++
这是我的代码中定义的标准 C++ ASSERT 宏 -
#ifndef DEBUG
#define ASSERT(n)
#else
#define ASSERT(n) \
if (!(n)){ \
printf("%s - Failed ", #n); \
printf("On %s ", __DATE__); \
printf("At %s ", __TIME__); \
printf("In File %s ", __FILE__); \
printf("At Line %d\n", __LINE__); \
exit(1);}
#endif
我想通过绑定单元测试来确保我的构建始终包含此代码。测试应检查是否未提供 #DEBUG 预处理器(即它是发布模式),单元测试中应用的条件检查应失败,ASSERT 宏失败并包含上面给出的消息。
是否有既定的方法来实现这一点?我正在使用 google 测试框架来实现这一点,但无法实现结果。测试失败并显示标准断言消息,而不是我尝试失败的自定义断言。
我的代码如下 -
TEST(VerifyNormalInitialization, VerifyAssert)
{
static int index = 0;
static int num = 4;
ASSERT(index == num);
EXPECT_FATAL_FAILURE(ASSERT(index == num),"Failed");
}
首先显而易见的是,当定义了 DEBUG 时,以下内容只会引发错误。
ASSERT(index == num);
ASSERT(index != num);
对于两种情况的单元测试:生产和开发,您需要两种方式都编译。
你可能会影响你自己 #define/#undef DEBUG
。
好的做法?我不知道;我不知道这是值得测试的东西。也许只是验证 ASSERT 在开发过程中处于活动状态。这是安装检查的内容。
考虑
EXPECT_FATAL_FAILURE(if (!(index == num)){ ... },"Failed");
这看起来像有效的 C++ 吗?不是。
考虑编写一个宏,将 #n
、__FILE__
等传递给适当的函数。如果您坚持单独使用宏,那么它需要是单个表达式而不是语句,类似于:
#define STR2(x) #x
#define STR(x) STR2(x)
#define ASSERT(n) \
( \
fprintf(stderr, \
#n " - Failed on " __DATE__ " at " __TIME__ \
" in file " __FILE__ " at line " STR(__LINE__) \
), \
exit(EXIT_FAILURE) \
)
这是使用 compile-time 字符串连接来准备整个字符串。此表达式中的所有内容都是字符串文字,并且 "hello"
和 "world"
等两个字符串文字被 pre-processor 连接为 "helloworld"
.
“字符串化”宏只是将整数 __LINE__
转换为字符串文字。 Stringification - how does it work?
注意),
是逗号运算符,用于允许在同一个表达式中调用两个函数。
这是我的代码中定义的标准 C++ ASSERT 宏 -
#ifndef DEBUG
#define ASSERT(n)
#else
#define ASSERT(n) \
if (!(n)){ \
printf("%s - Failed ", #n); \
printf("On %s ", __DATE__); \
printf("At %s ", __TIME__); \
printf("In File %s ", __FILE__); \
printf("At Line %d\n", __LINE__); \
exit(1);}
#endif
我想通过绑定单元测试来确保我的构建始终包含此代码。测试应检查是否未提供 #DEBUG 预处理器(即它是发布模式),单元测试中应用的条件检查应失败,ASSERT 宏失败并包含上面给出的消息。
是否有既定的方法来实现这一点?我正在使用 google 测试框架来实现这一点,但无法实现结果。测试失败并显示标准断言消息,而不是我尝试失败的自定义断言。 我的代码如下 -
TEST(VerifyNormalInitialization, VerifyAssert)
{
static int index = 0;
static int num = 4;
ASSERT(index == num);
EXPECT_FATAL_FAILURE(ASSERT(index == num),"Failed");
}
首先显而易见的是,当定义了 DEBUG 时,以下内容只会引发错误。
ASSERT(index == num);
ASSERT(index != num);
对于两种情况的单元测试:生产和开发,您需要两种方式都编译。
你可能会影响你自己 #define/#undef DEBUG
。
好的做法?我不知道;我不知道这是值得测试的东西。也许只是验证 ASSERT 在开发过程中处于活动状态。这是安装检查的内容。
考虑
EXPECT_FATAL_FAILURE(if (!(index == num)){ ... },"Failed");
这看起来像有效的 C++ 吗?不是。
考虑编写一个宏,将 #n
、__FILE__
等传递给适当的函数。如果您坚持单独使用宏,那么它需要是单个表达式而不是语句,类似于:
#define STR2(x) #x
#define STR(x) STR2(x)
#define ASSERT(n) \
( \
fprintf(stderr, \
#n " - Failed on " __DATE__ " at " __TIME__ \
" in file " __FILE__ " at line " STR(__LINE__) \
), \
exit(EXIT_FAILURE) \
)
这是使用 compile-time 字符串连接来准备整个字符串。此表达式中的所有内容都是字符串文字,并且 "hello"
和 "world"
等两个字符串文字被 pre-processor 连接为 "helloworld"
.
“字符串化”宏只是将整数 __LINE__
转换为字符串文字。 Stringification - how does it work?
注意),
是逗号运算符,用于允许在同一个表达式中调用两个函数。