当前位置: 首页 > news >正文

C++高性能日志库spdlog

spdlog简介

spdlog 是一个高性能的 C++ 日志库,它设计时充分考虑了速度和易用性,具有以下特点

  • 高效与快速:Spdlog 专注于提供极致的性能,在大量日志记录场景下也能保持较低的延迟和较高的吞吐量。

  • 低内存占用:Spdlog的设计确保了即使在高负载下,它也能保持低内存占用。

  • 轻量化设计:Spdlog 是头文件(header-only)库,这意味着用户只需要包含相应的头文件即可开始使用,无需编译链接额外的库文件。

  • 跨平台支持:它支持多种操作系统,包括但不限于 Windows、Linux 和 macOS,并且在这些平台上都能够良好运行。

  • 丰富的日志级别:Spdlog 支持常见的日志级别,如 TRACE、DEBUG、INFO、WARN、ERROR、CRITICAL 等,用户可以根据需要选择不同级别的日志输出。

  • 格式化与定位信息:通过集成 fmt 库,Spdlog 允许用户自定义日志消息的格式,可以轻松地包含时间戳、线程ID、文件名、行号以及函数名等上下文信息。

  • 多目标输出:可以将日志输出到控制台、普通文本文件、循环写入文件(rotating log files)、每日生成新文件(daily logs)、系统日志等目标,同时也支持异步写入以提高性能。

  • 线程安全:对于多线程环境,Spdlog 提供了线程安全的日志接口,确保在并发环境下日志记录的正确性和完整性。

  • 异步模式:提供可选的异步日志记录机制,能够将日志操作放入后台线程执行,从而避免阻塞主线程。

  • 条件日志:根据预定义的条件开关,可以动态启用或禁用特定级别的日志输出。


Spdlog下载


# 项目下载
git clone https://github.com/gabime/spdlog.git
#编译
cd spdlog
mkdir build
cd build
cmake ..
make -j
#安装
sudo make install#或者直接下载
sudo apt-get install libspdlog-dev

 Spdlog日志

1.日志的作用
  1. 问题排查与故障诊断
  2. 数据备份与恢复
  3. 系统监控与性能优化
  4. 安全审计与合规性检查
2.同步和异步的区别

        执行方式:

        同步:在同步日志记录中,应用程序在执行日志记录操作时,会暂停当前的业务流程,直到日志被成功写入到存储介质(如文件、数据库等)中。

        异步:而异步日志则是将日志记录操作放在一个单独的线程或队列中进行处理。当应用程序需要记录日志时,它只是将日志信息发送到一个缓冲区或队列中,然后继续执行后续的业务逻辑。

        性能:

        同步:由于同步日志会阻塞当前线程,等待日志写入完成,因此在高并发场景下,如果日志记录操作较为频繁,可能会导致业务线程的阻塞,从而影响整个应用程序的性能和响应时间。

        异步:异步日志由于不会阻塞业务线程,所以可以提高应用程序的性能和响应速度。在高并发情况下,它能够将日志记录的开销分散到后台线程,使得业务逻辑能够更快速地执。

3.Spdlog为什么高效
  •  零成本抽象:spdlog通过模板和内联函数来实现零成本抽象,确保只有在真正需要时才进行日志记录。
  • 异步日志记录:spdlog支持异步日志记录,这意味着它可以将日志信息发送到线程池进行处理,从而减少了对主线程性能的影响。
  • 高效地格式化:spdlog使用fmt库进行高效的字符串格式化,减少了格式化日志信息所需要的事件。
4.Spdlog处理流程 

         Loggers负责记录日志信息,Sinks决定了日志消息的输出位置,Formatters负责将日志信息转换为特定格式,AsyncLoffer异步地将日志消息写入到目标Sink中,Registry用于管理这些组件。

5. 相关问题

        1.多线程使用日志库,跟同步和异步是否有关联

           没有什么关联

        2.同一个线程处理的,是不是就是同步的

           如果时当前处理程序处理的那就是同步,如果仅仅是获得完成通知,那就只是协程上的同步

        3.为什么需要这么多的日志级别

           trece,debug,info,warn,error,critical

          从左到右,级别越来越高

级别用途描述
trace    最细节的日志,追踪变量,执行路径,性能分析时有用(函数级别打印)
debug调试信息,用于开发器观察程序逻辑,如状态变化(模块级别状态)
info一般运行信息,系统启动,任务完成,资源加载等(用户可以看到)
warn非致命问题,程序还可以运行,如配置异常,网络抖动(可忽略但需注意)
error程序运行失败,如读取文件失败,通信断开(需重点关注)
critical致命错误,系统可能崩溃或者立即介入,如系统异常终止(报警级别)

创建logger

获取实例是线程安全的

        1.工厂方法创建

auto logger = spdlog::srdout_color_mt("console");

        2.手动创建

auto sink = make_shared<spdlog::sinks::stdout_color_sink_mt>();
auto logger = make_shared<spdlog::logger>("logger",sink);
spdlog::register_logger(logger);

        3.注册logger,目的为了全局访问

spdlog::get("logger")->info("Hello from anywhere!");

创建sink

 已有的sink

stdout_color_sink_mt   //彩色终端输出basic_file_sink_mt     //写入基础文件rotating_file_sink_mt  //日志轮转(按照文件大小)daily_file_sink_mt     //每天生成一个日志文件null_sink_mt           //静默输出

 自定义sink

继承 spdlog::sink::base_sink sink 实现 sink_it_()flush_() 方法即可

自定义格式化

        1.set_pattern

spdlog::set_pattern("[%Y-%m-%d %H:%M:%S.%e] [%l] %v");

        2.flags

  • %v:日志内容
  • %t :   线程ID
  • %s:源文件名
  • %#:源代码行号
  • %!:函数名
  • %^ %$:高亮开头/结尾 

        3.源文件定位flags 

SPDLOG_LOGGER_CALL(logger,spdlog::level::info,"msg");

 创建异步日志

1.使用async_factory

#include "spdlog/async.h"
#include "spdlog/sinks/basic_file_sink.h"auto logger = spdlog::basic_logger_mt<spdlog::async_factory>("async_logger", "async.txt");

2.creat_async

auto sink = std::make_shared<spdlog::sinks::basic_file_sink_mt>("async.txt",true);
logger = spdlog::create_async("async_logger",sink);

 3.create_async_nb,非阻塞写法,不阻塞主线程写入日志

auto logger = spdlog::create_async_nb<spdlog::sink::basic_file_sink_mt>("async_nb_looger","nb.txt");

4.async_logger

spdlog::init_thread_pool(8192,1);auto sink = std::make_shared<spdlog::sinks::basic_file_sink_mt>("custom.txt",true);
auto async_logger = std::make_shared<spdlog::async_logger>("custom_async",sink,spdlog::thread_pool(),spdlog::async_overflow_policy::block);spdlog::register_logger(async_logger);

刷新策略

        1.手动flush

logger->flush();

        2.条件flush

spdlog::flush_on(spdlog::level::err);

        3.间隔flush

spdlog::flush_every(std::chrono::seconds(3));

实例演示

  控制台打印

  #include <spdlog/spdlog.h>#include <string.h>#include <iostream>int main(){// 普通打印spdlog::info("Welcome to info spdlog!");// 格式化打印// 打印字符串spdlog::info("Hello World {}", "spdlog!");// 打印数字spdlog::error("spdlog errCode : {}", -10020);// 指定打印数字的占位符spdlog::warn("spdlog format char {:08d}", 12);// 格式化打印不同进制的数据spdlog::critical("Support for int:{0:d} hex:{0:x} oct:{0:o} bin:{0:b}", 42);// 打印浮点型数据spdlog::info("float args are {:03.2f}", 1.23456);// 打印多个参数spdlog::info("string args are {0} {1}..", "too", "supported");spdlog::info("number args are {0} {1} {2}..", 10020, 10040, -100);system("pause");}

参数是以{},传入的。

资源分享:0voice · GitHub

http://www.xdnf.cn/news/195121.html

相关文章:

  • 深入浅出限流算法(二):更平滑的滑动窗口
  • Python 如何操作数据库,让你使用 DeepSeek 开发数据库应用更加快 (Orm Bee)
  • MySQL复合查询
  • HTML 从标签到动态效果的基础
  • react-navigation-draw抽屉导航
  • ArkTS基础实验 (二)
  • 数字人Live_Talking的搭建和使用
  • OpenResty深度解析:从卓伊凡的”隐形主流”论看其深度原理与应用生态-卓伊凡
  • 深入理解java线程池
  • stm32 阻塞式延时 与 非阻塞式延时
  • “数字驱动·智建未来——2025河北省建筑电气与智能化技术交流大会”
  • 【ACL系列论文写作指北14-科研心态与抗压管理】-走得远,比走得快更重要
  • 不同参数大小的DeepSeekR1模型对Java中new FileInputStream(“test.txt“).seek(100);语法错误的检查
  • 学习笔记:Qlib 量化投资平台框架 — MAIN COMPONENTS (Part I)
  • XrayR启动失败
  • 架构进阶:详解108页系统架构设计与详细设计知识讲座【附全文阅读】
  • 品融电商:全域电商代运营的领航者,驱动品牌长效增长
  • 第四章:Messaging and Memory
  • C语言中的指针详解
  • RSS‘25|CMU提出统一空中操作框架:以末端执行器为中心,无人机实现高精度遥操作
  • Cursor + Figma-Context-MCP ,让 Cursor 获取 Figma 设计图信息,实现 AI 生成页面的高度还原
  • 力扣面试150题--K 个一组翻转链表
  • 机器人--激光雷达
  • ESG跨境电商怎么样?esg跨境电商有哪些功用?
  • 阅读MySQL实战45讲第11天
  • uniapp打包apk如何实现版本更新
  • Spring MVC异常处理利器:深入理解HandlerExceptionResolver
  • SpringBoot实现接口防刷的5种高效方案详解
  • C#/.NET/.NET Core技术前沿周刊 | 第 36 期(2025年4.21-4.27)
  • AudioSet 音频中文类别