我们的项目使用一个宏在一行语句中使日志记录变得容易和简单,如下所示:
DEBUG_LOG(TRACE_LOG_LEVEL, "The X value = " << x << ", pointer = " << *x);
该宏将第二个参数转换为字符串流参数,并将其发送到常规 C++ 记录器。这在实践中效果很好,因为它使多参数日志记录语句非常简洁。然而,Scott Meyers 在Effective C++ 3rd Edition中说过, “通过使用内联函数的模板,您可以获得宏的所有效率以及常规函数的所有可预测行为和类型安全性”(第 2 项)。我知道 C++ 中宏的使用存在许多与可预测行为相关的问题,因此我试图在我们的代码库中消除尽可能多的宏。
我的日志记录宏定义类似于:
#define DEBUG_LOG(aLogLevel, aWhat) { \
if (isEnabled(aLogLevel)) { \
std::stringstream outStr; \
outStr<< __FILE__ << "(" << __LINE__ << ") [" << getpid() << "] : " << aWhat; \
logger::log(aLogLevel, outStr.str()); \
}
我已经尝试过几次将其重写为不使用宏的东西,包括:
inline void DEBUG_LOG(LogLevel aLogLevel, const std::stringstream& aWhat) {
...
}
和...
template<typename WhatT> inline void DEBUG_LOG(LogLevel aLogLevel, WhatT aWhat) {
... }
无济于事(上述 2 次重写都不会针对第一个示例中的日志记录代码进行编译)。还有其他想法吗?这可以做到吗?还是最好将其保留为宏?