我正在进行一个较小的项目,大约有3-4人。我希望能够通过日志等方式拥有一种可靠的调试应用程序的方法。有没有关于如何构建它的好资源呢?我听说过许多项目经理说一个良好的日志功能对每个项目都至关重要,但我不确定如何做到这一点。
我正在进行一个较小的项目,大约有3-4人。我希望能够通过日志等方式拥有一种可靠的调试应用程序的方法。有没有关于如何构建它的好资源呢?我听说过许多项目经理说一个良好的日志功能对每个项目都至关重要,但我不确定如何做到这一点。
stderr
,那么你可以使用我编写的这个类:#ifndef _LOGGER_HPP_
#define _LOGGER_HPP_
#include <iostream>
#include <sstream>
/* consider adding boost thread id since we'll want to know whose writting and
* won't want to repeat it for every single call */
/* consider adding policy class to allow users to redirect logging to specific
* files via the command line
*/
enum loglevel_e
{logERROR, logWARNING, logINFO, logDEBUG, logDEBUG1, logDEBUG2, logDEBUG3, logDEBUG4};
class logIt
{
public:
logIt(loglevel_e _loglevel = logERROR) {
_buffer << _loglevel << " :"
<< std::string(
_loglevel > logDEBUG
? (_loglevel - logDEBUG) * 4
: 1
, ' ');
}
template <typename T>
logIt & operator<<(T const & value)
{
_buffer << value;
return *this;
}
~logIt()
{
_buffer << std::endl;
// This is atomic according to the POSIX standard
// http://www.gnu.org/s/libc/manual/html_node/Streams-and-Threads.html
std::cerr << _buffer.str();
}
private:
std::ostringstream _buffer;
};
extern loglevel_e loglevel;
#define log(level) \
if (level > loglevel) ; \
else logIt(level)
#endif
使用方法如下:
// define and turn off for the rest of the test suite
loglevel_e loglevel = logERROR;
void logTest(void) {
loglevel_e loglevel_save = loglevel;
loglevel = logDEBUG4;
log(logINFO) << "foo " << "bar " << "baz";
int count = 3;
log(logDEBUG) << "A loop with " << count << " iterations";
for (int i = 0; i != count; ++i)
{
log(logDEBUG1) << "the counter i = " << i;
log(logDEBUG2) << "the counter i = " << i;
}
loglevel = loglevel_save;
}
#define log(level) \ if (level > loglevel) ; \ else logIt(level)
给了我很多错误。它说 语法错误:if
和 语法错误:else
。有什么想法吗?Visual Studio 2012 Express - Boyang#define
语句保留为三个单独的行?你必须确保反斜杠\字符后面没有空格或其他任何内容。 - Robert S. Barneslogger.hpp
来解决了这个问题。我在这里提出了一个单独的问题 http://stackoverflow.com/questions/19795038/can-define-preprocessor-directive-contain-if-and-else/19795951?noredirect=1#19795951 - Boyangif (level > loglevel) ; \
中的分号应该被空块 {} 替换吗? - Boyangif (level > loglevel) ; \\
中的分号是否应该被空块 {} 替换?如果不是,log(levelDEBUG) << "test"
将变成 if (logDEBUG > loglevel); else logIt(logInfo) << "foo " << "bar " << "baz";
,而 else 将没有 if 可以附加,因为分号关闭了 if,不是吗?实际上,为什么不只是做 #define log(level) if (level <= loglevel)
呢?我对预处理器指令不太了解。谢谢! - Boyanglog4cxx
具有非常灵活的配置,可以通过它对输出目标(文件/旋转文件/控制台等)、子组件的调试级别(例如,你希望集中关注特定类/组件,因此将其设置为DEBUG
级别,而其余部分则为INFO
级别)、日志条目格式等进行控制,而无需重新编译。取决于你所说的“日志记录”是什么意思。一种形式就是提供一种方法,将某个对象的内容打印到输出流中。对于类型为 ClassName 的对象,这需要为该类编写插入运算符:
std::ostream &operator<< (std::ostream &stream, const ClassName & obj) {
// Implementation elided
}
有了这个,您可以将 ClassName 类型的对象打印到输出流中。这非常有用,以至于一些组织要求每个类都实现这样的方法。