控制台仅在调试模式c ++中输出

时间:2015-08-06 15:48:00

标签: c++ debugging c++11 clion

我原以为这是一个广泛问的问题,但我还没有找到答案。

我正在调试一些C ++代码,这些代码只是以某些函数句柄作为输入以微妙的方式创建错误。长话短说明了问题,但我在.cpp文件中定义:

#define DEBUG(x) do { std::cerr << x << std::endl; } while (0)

不用说代码充斥着:

DEBUG("Foo's address") 
DEBUG(&Foo)

现在我假设在&#34;发布&#34;编译器会忽略所有这些预编译器输出。但它没有!

那么在实践中如何做到这一点(我想留下未来添加的输出,但显然不希望它在发布版本中)?我正在尝试使用cmake的clion,这是IDE /编译器特有的吗?

由于

3 个答案:

答案 0 :(得分:2)

根据您的编译器,它可能会定义一些东西,告诉您编译处于调试模式(或者您可以在命令行上自己完成),然后:

#ifndef _DEBUG // works in VS
#define DEBUG(x) 
#else
#define DEBUG(x) do { std::cerr << x << std::endl; } while (0)
#endif

有关使用哪个宏的更多讨论,请参阅this问题。

答案 1 :(得分:1)

这样做的便携方法是使用NDEBUG

#ifdef NDEBUG
#define DEBUG(x) 
#else
#define DEBUG(x) do { std::cerr << x << std::endl; } while (0)
#endif

请参阅:C / C++ : Portable way to detect debug / release?

答案 2 :(得分:0)

在所谓的&#34;发布版本&#34;中消除日志消息通常是错误的。毕竟,&#34;发布版本&#34;是您最需要记录信息的地方!当最终用户除了&#34;它没有工作&#34; 或&#34; 之外,你甚至希望分析并解决问题。它崩溃了&#34;?

因此,不要消除软件创建的有价值的信息,以帮助您进行错误修正会话,而是考虑如何保存和保存它,以便在出现问题时最终用户可以轻松地将其传输给您。比如,当应用程序在用户的计算机上运行时,将日志消息重定向到日志文件(可能是应用程序本身提供了一个&#34;发送日志文件以支持&#34;功能,或类似的东西)。

代码

DEBUG("Foo's address") 
DEBUG(&Foo)

应该替换为:

Log("Foo's address");
Log(std::to_string(&Foo));

然后在您的Log函数内部,可能会有void Log(std::string const& message)这样的签名,您可以检查DEBUG宏并采取相应的行动:

    void Log(std::string const& message)
    {
#ifdef DEBUG
        // write message to std::cerr
#else
        // write message to log file
#endif
    }

现在,当然,DEBUG 不是标准宏(与NDEBUG不同,后者会打开和关闭assert)。它没有隐式定义。您必须在调用编译器时自己定义它。例如,/DDEBUG与MSVC或-DDEBUG与GCC。有可能你的IDE在运行编译器时添加了这样的标志或类似-D_DEBUG之类的东西,但是,它仍然不是标准的,也不是编译器本身的一部分。 (实际上,如果您打算像LOG_TO_CONSOLE那样使用它,您可能会考虑使用宏的不同名称。)

无论如何,这只是为了给你一个做什么的灵感。您可能更喜欢基于std::ostream的方法,而不是采用std::string的函数。 Stackoverflow上有很多问题和答案。

重要的一点是:假设您的软件一旦发布就不再需要,请不要丢弃有价值的日志信息。会有错误和模糊的错误描述。