官方网站GitHub:
https://github.com/log4cplus
https://github.com/log4cplus/log4cplus
最新版需要C++2017,罢了
我用的是C++11的一个tag版本: https://github.com/log4cplus/log4cplus/tree/REL_2_0_4
下载解压,VS2017打开msvc14里的log4cplus.sln文件,
1 用CMake打开源码根目录
2 必须设置Unicode (所有工程:不管是log4cplus工程本身,还是其他任何用log4cplus的工程)
3 VS项目》属性》C/C++》语言》将WChar_t视为内置类型》否 (所有工程:不管是log4cplus工程本身,还是其他任何用log4cplus的工程)
4 QTCore-Dir C:/Qt/Qt5.11.2/5.11.2/msvc2017_64/lib/cmake/Qt5Core
5 设置LOG4CPLUS_QT5
异步模式需要开启,不然多线程同时写日志会有问题
需要到
https://github.com/log4cplus/ThreadPool
把.h和.cpp文件下载下来,放到
E:\log4cplus\log4cplus-REL_2_0_4\threadpool 目录里
下载:Catch-master.zip 解压后,把文件夹中的内容复制到 log4cplus-REL_2_0_4\catch中
编译log4cplus这个dll工程
生成对应的
log4cplusD.lib/dll
log4cplus.lib/dll
直接添加到工程中使用即可。
log4cplus::Initializer initializer;
log4cplus::SharedAppenderPtr rollingFileAppender(new log4cplus::RollingFileAppender(LOG4CPLUS_TEXT("My.log"), 5 * 1024 * 1024, 10, true, true));
rollingFileAppender->setName(LOG4CPLUS_TEXT("MyRollingFileAppender"));
log4cplus::SharedAppenderPtr asyncAppender(new log4cplus::AsyncAppender(rollingFileAppender, 100));
auto pattern = LOG4CPLUS_TEXT("[%D{%Y-%m-%d %A %p %H:%M:%S %q}] [%-5p] %m [%l] [%c] [%t]%n");
rollingFileAppender->setLayout(std::unique_ptr(new log4cplus::PatternLayout(pattern)));
log4cplus::Logger logger(log4cplus::Logger::getInstance(LOG4CPLUS_TEXT("MyLogger")));
logger.addAppender(asyncAppender);
退出log4cplus
//! Per thread cleanup function. Users should call this function before
//! a thread ends its execution. It frees resources allocated in thread local
//! storage. It is important only for multi-threaded static library builds
//! of log4cplus and user threads. In all other cases the clean up is provided
//! automatically by other means.
LOG4CPLUS_EXPORT void threadCleanup ();
/**
* Calling this method will safely close and remove all
* appenders in all the loggers including root contained in the
* default hierachy.
*
* Some appenders such as SocketAppender need to be closed before the
* application exits. Otherwise, pending logging events might be
* lost.
*
* The shutdown
method is careful to close nested
* appenders before closing regular appenders. This is allows
* configurations where a regular appender is attached to a logger
* and again to a nested appender.
*/
static void shutdown();
log4cplus::Initializer
构造函数调用log4cplus::initialize(),析构函数调用log4cplus::Logger::shutdown()
log4cplus::Initializer m_initializer;//构造函数调用log4cplus::initialize(),析构函数调用log4cplus::Logger::shutdown()
还没完:当你使用了ThreadPool之后,log4cplus总是会在main函数执行之前使用static机制初始化,并创建线程池。如果你在main函数退出的时候没有调用
log4cplus::deinitialize();
则线程池中的线程不会退出。导致main函数无法退出。所以要在main函数退出之前调用这句话,如果不调用,那个log4cplus::Initializer m_initializer;只负责调用shutdown,而不负责调用clearThreadPool。只有log4cplus::deinitialize();才会既clearThreadPool又shutdown
非常详细介绍log4cplus的博客:
https://blog.csdn.net/lx_shudong/article/details/48732999
LogLog类实现了debug, warn, error 函数用于logcplus运行时显示log4cplus自身的调试、警告或错误信息,是对标准输出的简单封装,它也可以用来进行简单的日志输出。
PatterLayout支持的转换标识符主要包括:
(1)"%%",转义为%, 即,std::string pattern = "%%" 时输出"%"。
(2)"%c",输出logger名称,比如std::string pattern ="%c" 时输出: "test_logger.subtest", 也可以控制logger名称的显示层次,比如"%c{1}"时输出"test_logger",其中数字表示层次。
(3)"%D",显示本地时间,当std::string pattern ="%D" 时输出:"2004-10-16 18:55:45",%d显示标准时间,所以当std::string pattern ="%d" 时输出"2004-10-16 10:55:45" (因为北京时间位于东8区,差8个小时)。
可以通过%d{...}定义更详细的显示格式,比如%d{%H:%M:%s}表示要显示小时:分钟:秒。大括号中可显示的预定义标识符如下:
%a -- 表示礼拜几,英文缩写形式,比如"Fri"
%A -- 表示礼拜几,比如"Friday"
%b -- 表示几月份,英文缩写形式,比如"Oct"
%B -- 表示几月份,"October"
%c -- 标准的日期+时间格式,如 "Sat Oct 16 18:56:19 2004"
%d -- 表示今天是这个月的几号(1-31)"16"
%H -- 表示当前时刻是几时(0-23),如 "18"
%I -- 表示当前时刻是几时(1-12),如 "6"
%j -- 表示今天是哪一天(1-366),如 "290"
%m -- 表示本月是哪一月(1-12),如 "10"
%M -- 表示当前时刻是哪一分钟(0-59),如 "59"
%p -- 表示现在是上午还是下午, AM or PM
%q -- 表示当前时刻中毫秒部分(0-999),如 "237"
%Q -- 表示当前时刻中带小数的毫秒部分(0-999.999),如 "430.732"
%S -- 表示当前时刻的多少秒(0-59),如 "32"
%U -- 表示本周是今年的第几个礼拜,以周日为第一天开始计算(0-53),如 "41"
%w -- 表示礼拜几,(0-6, 礼拜天为0),如 "6"
%W -- 表示本周是今年的第几个礼拜,以周一为第一天开始计算(0-53),如 "41"
%x -- 标准的日期格式,如 "10/16/04"
%X -- 标准的时间格式,如 "19:02:34"
%y -- 两位数的年份(0-99),如 "04"
%Y -- 四位数的年份,如 "2004"
%Z -- 时区名,比如 "GMT"
(4)"%F",输出当前记录器所在的文件名称,比如std::string pattern ="%F" 时输出: "main.cpp"。
(5)"%L",输出当前记录器所在的文件行号,比如std::string pattern ="%L" 时输出: "51"
(6)"%l",输出当前记录器所在的文件名称和行号,比如std::string pattern ="%l" 时输出"main.cpp:51"。
(7)"%m",输出原始信息,比如std::string pattern ="%m" 时输出: "teststr",即上述代码中LOG4CPLUS_DEBUG的第二个参数,这种实现机制可以确保原始信息被嵌入到带格式的信息中。
(8)"%n",换行符,没什么好解释的。
(9)"%p",输出LogLevel,比如std::string pattern ="%p" 时输出: "DEBUG"。
(10)"%t",输出记录器所在的线程ID,比如std::string pattern ="%t" 时输出: "1075298944"。
(11)"%x",嵌套诊断上下文NDC (nested diagnostic context) 输出,从堆栈中弹出上下文信息,NDC可以用对不同源的log信息(同时地)交叉输出进行区分,关于NDC方面的详细介绍会在下文中提到。
(12)格式对齐,比如std::string pattern ="%-10m"时表示左对齐,宽度是10,此时会输出"teststr ",当然其它的控制字符也可以相同的方式来使用,比如"%-12d","%-5p"等等。
个人喜欢的一种自己定义的pattern:
std::string pattern = "[%D{%Y-%m-%d %A %p %H:%M:%S %q}] [%-5p] %m [%l]%n";
输出:
[2019-08-20 Tuesday AM 09:38:25 106] [WARN ] Hello World! 你好世界!100分 [e:\product\test\main.cpp:51]
但是这个模式在release模式下输出的星期几是汉字,而且输出不了。
//%A 星期几 %p 上午还是下午,Release模式会乱码
auto pattern = LOG4CPLUS_TEXT("[%D{%Y-%m-%d %A %p %H:%M:%S %q}] [%-5p] %m [%l] [%c] [%t]%n");
需要在日志初始化log4cplus::initialize()之前加上
std::locale::global(std::locale(""));
输出样式如下:
[2019-08-23 星期五 下午 19:17:43 268] [WARN ] Hello World! [e:\product-\trunk\test\test_main.cpp:75] [MyTest] [19,028]
C/C++程序中,locale(即系统区域设置,即国家或地区设置)将决定程序所使用的当前语言编码、日期格式、数字格式及其它与区域有关的设置,locale设置的正确与否将影响到程序中字符串处理(wchar_t如何输出、strftime()的格式等)。因此,对于每一个程序,都应该慎重处理locale设置。
C locale和C++ locale是独立的。C locale用setlocale(LC_CTYPE, “”)初始化,
C++ locale用std::locale::global(std::locale(“”))初始化。这样就可以根据当前运行环境正确设置locale。
是在PatternLayout基础上发展的一种缺省的带格式输出的布局器,其格式由时间,线程ID,Logger和NDC 组成(consists of time, thread, Logger and nested diagnostic context information, hence the name),因而得名。
重定向是指把日志写的目的地是哪里:控制台、文件。
log4cplus默认将输出到控制台,提供ConsoleAppender用于操作。示例代码请参见4.2.1、4.2.2或4.2.3小节,这里不再赘述。
log4cplus提供了三个类用于文件操作,它们是FileAppender类、RollingFileAppender类、DailyRollingFileAppender类。
头文件:
#include "log4cplus/consoleappender.h"
#include
log4cplus::SharedAppenderPtr consoleAppend(new log4cplus::ConsoleAppender());
log4cplus::SharedAppenderPtr rollingFileAppender(new log4cplus::RollingFileAppender("MyLog.log", 5 * 1024 * 1024, 10, true));
Log4cplus配置文件的使用(学习笔记)
使用Log4Cplus+配置文件打印日志
log4cplus将输出的log信息按照LogLevel(从低到高)分为:
级别 |
说明 |
NOT_SET_LOG_LEVEL ( -1) |
接受缺省的LogLevel,如果有父logger则继承它的LogLevel |
ALL_LOG_LEVEL (0) |
开放所有log信息输出 |
TRACE_LOG_LEVEL (0) |
开放trace信息输出(即ALL_LOG_LEVEL) |
DEBUG_LOG_LEVEL(10000) |
开放debug信息输出 |
INFO_LOG_LEVEL (20000) |
开放info信息输出 |
WARN_LOG_LEVEL (30000) |
开放warning信息输出 |
ERROR_LOG_LEVEL(40000) |
开放error信息输出 |
FATAL_LOG_LEVEL (50000) |
开放fatal信息输出 |
OFF_LOG_LEVEL (60000) |
关闭所有log信息输出 |
报错:error LNK2019: 无法解析的外部符号 "class std::basic_ostringstream
生成log4cplus的工程,字节编码和使用log4cplus库的工程字节编码不一致导致。参考