spdlog框架的安装与使用
- spdlog的安装
- spdlog的使用
- spdlog二次封装
- 总结:
spdlog的安装
sudo apt-get install libspdlog-dev
spdlog的使用
同步日志器sync.cc
(输出到显示器/输出到指定文件)
#include<spdlog/spdlog.h>
#include<spdlog/sinks/stdout_color_sinks.h>
#include<spdlog/sinks/basic_file_sink.h>
#include<iostream>int main()
{//设置全局的刷新策略,每秒刷新一次spdlog::flush_every(std::chrono::seconds(1));//遇到debug以上级别的日志立刻刷新spdlog::flush_on(spdlog::level::level_enum::debug);//设置全局的日志输出等级spdlog::set_level(spdlog::level::level_enum::debug);//创建同步日志器(模板默认是同步工厂,不需要写,标准输出,输出到显示器上)//auto logger=spdlog::stdout_color_mt("defaut-logger");//创建同步日志器(文件输出,输出到文件上)auto logger=spdlog::basic_logger_mt("file-logger","sync_file.log");//设置日志器的刷新策略,以及输出等级,但是已经有了全局的就可以不用局部的// logger->flush_on(spdlog::level::level_enum::debug);// logger->set_level(spdlog::level::level_enum::debug);//设置日志的输出格式、logger->set_pattern("[%H:%M:%S][%t][%n][%-8l] %v");//进行简单的日志输出logger->trace("你好!{}","陶恩威");logger->debug("你好!{}","陶恩威");logger->info("你好!{}","陶恩威");logger->warn("你好!{}","陶恩威");logger->error("你好!{}","陶恩威");logger->critical("你好!{}","陶恩威");std::cout<<"日志输出完毕\n";return 0;
}
makefile:
sync:sync.ccg++ -std=c++17 $^ -o $@ -lspdlog -lpthread
异步日志器:async.cc
(输出到显示器/输出到指定文件)
#include<spdlog/spdlog.h>
#include<spdlog/sinks/stdout_color_sinks.h>
#include<spdlog/sinks/basic_file_sink.h>
#include<spdlog/async.h>
#include<iostream>
//异步日志器跟同步日志器的使用没有区别,只不过在创建时,需要使用异步工厂日志器模板
int main()
{//设置全局的刷新策略,每秒刷新一次spdlog::flush_every(std::chrono::seconds(1));//遇到debug以上级别的日志立刻刷新spdlog::flush_on(spdlog::level::level_enum::debug);//设置全局的日志输出等级spdlog::set_level(spdlog::level::level_enum::debug);//创建异步日志器(模板默认是同步工厂,创建异步就需要指定异步工厂,标准输出,输出到显示器上),会将后面的先输出//而原本的日志输出后输出,因为日志先放入了内存中,由线程池输出//auto logger=spdlog::stdout_color_mt<spdlog::async_factory>("defaut-logger");//异步日志器,文件输出auto logger=spdlog::basic_logger_mt<spdlog::async_factory>("file-logger","async_file.log");//设置日志的输出格式、logger->set_pattern("[%H:%M:%S][%t][%n][%-8l] %v");//进行简单的日志输出logger->trace("你好!{}","陶恩威");logger->debug("你好!{}","陶恩威");logger->info("你好!{}","陶恩威");logger->warn("你好!{}","陶恩威");logger->error("你好!{}","陶恩威");logger->critical("你好!{}","陶恩威");std::cout<<"日志输出完毕\n";return 0;
}
makefile:
async:async.ccg++ -std=c++17 $^ -o $@ -lspdlog -lpthread
spdlog二次封装
spdlog日志输出没有文件名和行号,而一般项目中都要有对应的文件名以及行号,所以原本的spdlog就不好用,所以要封装一下,让其能够打印行号与文件名。
要对日志的初始化接口进行封装
要对日志的输出接口进行封装
logger.hpp
//对日志器进行二次封装
//1.因为原来的日志格式中没有文件名和行号,所以要进行封装
//2.为了便于操作,通过命令行参数来决定创建日志器输出在哪里:
/*如果是debug模式则输出到标准输出中.如果是发布模式则输出到文件中*/#include<spdlog/spdlog.h>
#include<spdlog/sinks/stdout_color_sinks.h>
#include<spdlog/sinks/basic_file_sink.h>
#include<spdlog/async.h>
//初始化日志器,有三个参数
//1.mode 表示运行的模式,true代表是发布模式,false代表是dubug模式
//2.file 表示如果是发布模式,日志输出的文件名叫什么,在debug模式下为空
//3.level 发布模式下,输出的日志等级是什么,在debug模式下为0.
std::shared_ptr<spdlog::logger> default_logger;
void init_logger(bool mode,const std::string&file,uint32_t level)
{if(mode==false){//调试debug模式下,则创建标准输出日志器,日志器的等级最低为0,刷新策略也是最低default_logger=spdlog::stdout_color_mt("defaut-logger");default_logger->set_level(spdlog::level::level_enum::trace);default_logger->flush_on(spdlog::level::level_enum::trace);}else{//发布模式下,则创建文件输出日志器,日志器的等级为level,刷新策略也是leveldefault_logger=spdlog::basic_logger_mt("file-logger",file);default_logger->set_level((spdlog::level::level_enum)level);default_logger->flush_on((spdlog::level::level_enum)level);}//创建完日志器之后,就要设置日志器的输出格式default_logger->set_pattern("[%H:%M:%S][%t][%n][%-8l]%v");
}//日志器初始化完后,就要对日志器的输出进行封装,因为日志器的输出格式中没有文件名和行号,利用宏定义来修改
#define TRACE_LOG(format,...) default_logger->trace(std::string("[{}:{}]")+format,__FILE__,__LINE__,##__VA_ARGS__);
#define DEBUG_LOG(format,...) default_logger->debug(std::string("[{}:{}]")+format,__FILE__,__LINE__,##__VA_ARGS__);
#define INFO_LOG(format,...) default_logger->info(std::string("[{}:{}]")+format,__FILE__,__LINE__,##__VA_ARGS__);
#define ERROR_LOG(format,...) default_logger->error(std::string("[{}:{}]")+format,__FILE__,__LINE__,##__VA_ARGS__);
#define FATAL_LOG(format,...) default_logger->critical(std::string("[{}:{}]")+format,__FILE__,__LINE__,##__VA_ARGS__);
使用样例:
mian.cc
#include "logger.hpp"
#include <gflags/gflags.h>
#include<iostream>
//想通过命令行参数调整变量的内容,所以通过gflags框架捕捉命令行参数数据放入到自己定义的全局变量中
DEFINE_bool(run_mode,false,"表示程序的运行模式,默认是false调试默认,true表示发布模式");
DEFINE_string(file,"","表示发布模式下要输出的文件名称,默认调试模式下为空");
DEFINE_int32(level,0,"表示发布模式下日志器输出的等级,默认调试模式下为0");int main(int argc,char*argv[])
{//首先初始化gflags框架,告诉它要捕捉命令行中的参数数据google::ParseCommandLineFlags(&argc, &argv, true);//初始化spdlog日志器;init_logger(FLAGS_run_mode,FLAGS_file,FLAGS_level); //日志输出TRACE_LOG("你好呀 {}","陶恩威");DEBUG_LOG("你好呀 {}","陶恩威");INFO_LOG("你好呀 {}","陶恩威");ERROR_LOG("你好呀 {}","陶恩威");FATAL_LOG("你好呀 {}","陶恩威");return 0;
}
makefile:
main:main.ccg++ -std=c++17 $^ -o $@ -lspdlog -lpthread -lgflags
总结:
spdlog日志库封装与使用
本文介绍了spdlog日志库的安装、基本使用和二次封装方法。主要内容包括:
spdlog安装:通过apt-get install libspdlog-dev命令安装
基本使用:
同步日志器:支持输出到显示器或文件
异步日志器:使用线程池提高性能
二次封装:
封装了日志初始化接口,支持通过命令行参数控制日志输出模式(debug/发布)
封装了日志输出宏,添加了文件名和行号信息
使用gflags框架处理命令行参数
示例代码展示了如何初始化日志器和输出不同级别的日志信息
封装后的日志库更方便在项目中使用,能够自动记录文件名和行号,并通过命令行参数灵活控制日志行为。