C++依赖管理与高效日志实践:vcpkg与spdlog的完美结合

发布时间:2026/7/25 6:24:51

C++依赖管理与高效日志实践:vcpkg与spdlog的完美结合 1. 项目概述为什么我们需要vcpkg和spdlog如果你在 Windows 上搞过 C 项目尤其是需要集成第三方库的时候大概率经历过“依赖地狱”。下载源码、配置编译选项、解决库之间的版本冲突、处理动态链接库路径……一套流程下来半天时间就没了而且换台机器很可能还得重来一遍。vcpkg的出现就是为了把 C 开发者从这个泥潭里拉出来。它是微软开源的一个跨平台 C/C 包管理器你可以把它想象成 Python 的pip或者 Node.js 的npm但专门服务于 C 生态。它的核心价值在于自动化地为你下载、编译、安装和管理数百个开源库并且能无缝集成到 Visual Studio、CMake 等主流构建系统中。而spdlog则是这个生态中一个极具代表性的“明星库”。它是一个非常快速、仅包含头文件的 C 日志库。在 C 的世界里写日志是个高频且基础的需求但自己从头实现一个高性能、线程安全的日志器并不容易。spdlog的出现让开发者可以用几行代码就获得一个功能强大、性能优异的日志解决方案。它支持控制台、文件、系统日志等多种输出方式格式自定义也非常灵活。那么把这两者结合起来——用vcpkg来安装和管理spdlog——就形成了一套极其高效的 C 开发工作流。你不再需要手动去 GitHub 下载spdlog的源码研究它的 CMake 配置或者处理可能的依赖。只需要一条简单的命令vcpkg就会帮你搞定一切让你可以立刻在代码中#include spdlog/spdlog.h并开始使用。这对于快速原型开发、学习新库甚至是大型项目的依赖管理都是一个巨大的效率提升。接下来我会带你从零开始完整走一遍这个流程并分享一些我踩过坑后才总结出来的实战经验。2.vcpkg的安装与环境配置2.1 获取与安装vcpkgvcpkg的安装方式非常“极客”它本身就是一个 CMake 项目需要通过 Git 克隆和脚本来引导安装。这种方式虽然初看有点原始但保证了最大的灵活性和跨平台一致性。首先你需要一个终端。在 Windows 上我强烈推荐使用PowerShell最好是管理员权限或者 Windows Terminal而不是传统的 CMD。因为后续的一些脚本如bootstrap-vcpkg.bat在 PowerShell 下运行更顺畅。第一步是克隆仓库。选择一个你希望安装vcpkg的目录这个目录路径最好不要包含中文或空格这是为了避免后续编译和路径处理时可能出现的各种诡异问题。我通常会在C:\或D:\根目录下创建一个Dev或Tools文件夹。# 打开 PowerShell切换到目标目录例如 D:\Dev cd D:\Dev # 克隆 vcpkg 仓库 git clone https://github.com/microsoft/vcpkg.git克隆完成后进入vcpkg目录你会看到一个bootstrap-vcpkg.bat脚本Windows或bootstrap-vcpkg.shLinux/macOS。运行这个脚本它会自动下载一个预先编译好的vcpkg可执行文件。cd vcpkg .\bootstrap-vcpkg.bat如果一切顺利你会看到类似 “vcpkg.exewas built successfully.” 的提示。此时当前目录下就生成了vcpkg.exe这个核心程序。注意有些网络环境下直接克隆 GitHub 或运行引导脚本可能会很慢甚至失败。这里就体现出vcpkg的一个巨大优势它支持镜像源。你可以通过设置环境变量VCPKG_DOWNLOADS来指定一个本地的下载缓存目录或者更彻底地为vcpkg本身配置一个镜像仓库。国内有一些社区维护的镜像可以显著提升包下载速度。不过配置镜像涉及修改vcpkg的配置文件我们稍后在“优化与配置”部分详细说明。2.2 集成到系统环境与开发工具安装好vcpkg.exe只是第一步要让它在日常开发中发挥作用还需要进行“集成”。1. 集成到系统环境变量推荐这是最方便的一步目的是让你可以在任何终端路径下直接输入vcpkg命令。将vcpkg.exe所在的目录例如D:\Dev\vcpkg添加到系统的PATH环境变量中。右键点击“此电脑” - “属性” - “高级系统设置” - “环境变量”。在“系统变量”或“用户变量”中找到Path点击编辑。新建一条填入你的vcpkg目录完整路径然后确定所有对话框。完成后重新打开一个终端输入vcpkg --version如果能看到版本信息说明集成成功。2. 集成到 Visual StudioWindows 用户必看这是vcpkg在 Windows 上最强大的功能之一全局集成。执行以下命令vcpkg integrate install这个命令会做两件关键事情它将vcpkg安装的所有库的头文件路径和库文件路径添加到 Visual Studio 的全局搜索目录中。这意味着只要你用 Visual Studio 打开任何一个项目IDE 就能自动找到通过vcpkg安装的库无需在项目属性里手动添加包含目录和库目录。它启用“自动链接”功能。对于支持此功能的库如spdlog你只需要#include对应的头文件Visual Studio 在编译时会自动帮你链接正确的.lib文件极大简化了项目配置。重要提示integrate install是用户级别的操作它修改的是当前用户的 Visual Studio 配置。如果你需要为所有用户安装或者想移除集成可以使用vcpkg integrate remove。我建议在初次使用时就执行集成它能避免后续大量的手动配置工作。3. 与 CMake 项目协同工作如果你使用 CMake 作为构建系统这也是现代 C 项目的趋势vcpkg提供了完美的支持。你不需要运行integrate install而是通过一个叫“工具链文件”的机制。 在使用 CMake 配置cmake -B build时通过-DCMAKE_TOOLCHAIN_FILE参数指定vcpkg提供的工具链文件路径cmake -B build -DCMAKE_TOOLCHAIN_FILED:/Dev/vcpkg/scripts/buildsystems/vcpkg.cmakeCMake 在配置阶段会读取这个文件从而自动发现所有通过vcpkg安装的包并在find_package()命令中生效。这是跨平台项目的最佳实践能保证团队中每个成员、每台构建服务器都使用完全一致的依赖版本和路径。3. 使用vcpkg安装与管理spdlog3.1 查找与安装包环境配置好后安装库就变得异常简单。首先你可以搜索vcpkg中是否包含你需要的库vcpkg search spdlog你会看到输出中包含spdlog以及它的简要描述和版本信息。这确认了该库在vcpkg的“食谱”ports列表中。安装命令的核心是vcpkg installvcpkg install spdlog这条命令会触发一系列自动化操作解析依赖vcpkg会读取spdlog的“食谱”文件ports/spdlog/portfile.cmake和CONTROL分析它是否需要其他库作为依赖。对于spdlog它是一个纯头文件库但可能依赖fmt库来进行格式化输出。下载源码从 GitHub 等官方源下载指定版本的spdlog源代码。编译构建虽然spdlog是头文件库但vcpkg的安装过程依然会执行其 CMake 配置流程以确保环境正确。对于需要编译的库如openssl,boostvcpkg会调用 CMake 或 Meson 等构建系统进行编译。安装到本地仓库将编译好的头文件、库文件等安装到vcpkg的installed目录下并按平台x86-windows,x64-windows等和编译类型debug,release分类存放。默认情况下vcpkg会为当前主机的默认架构安装库。在 Windows 上这通常是x86-windows。如果你想为 64 位系统安装需要显式指定三元组vcpkg install spdlog:x64-windows三元组是vcpkg的核心概念之一格式为[架构]-[平台]-[链接库类型]它精确定义了库的构建目标。常见的如x86-windows: 32位 Windows动态链接 (/MD)x64-windows: 64位 Windows动态链接 (/MD)x64-windows-static: 64位 Windows静态链接 (/MT)x64-linux: 64位 Linuxarm64-uwp: ARM64 架构的通用 Windows 平台应用3.2 理解安装目录结构与“清单模式”安装完成后所有库都位于vcpkg根目录下的installed文件夹中。其结构非常有条理installed/ ├── vcpkg/ │ └── ... (vcpkg自身信息) ├── x64-windows/ │ ├── include/ # 所有库的头文件都平铺在这里 │ ├── lib/ # 导入库 (.lib) 和静态库 (.a) │ ├── bin/ # 动态链接库 (.dll) 和可执行文件 │ ├── debug/ │ │ ├── lib/ # Debug 版本的库 │ │ └── bin/ │ └── share/ # 文档、CMake配置文件等 └── x86-windows/ └── ... (类似结构)这种“平铺”结构所有库的头文件都在同一个include下正是vcpkg integrate和工具链文件能生效的基础。你的编译器可以一次性扫描所有已安装的库。对于个人学习或小型项目直接用vcpkg install安装到全局installed目录很方便。但对于团队协作的正式项目我强烈推荐使用“清单模式”。清单模式的核心是在项目的根目录下放置两个文件vcpkg.json一个清单文件声明本项目所依赖的所有库及其版本约束。vcpkg-configuration.json可选用于配置注册表、覆盖项等。例如你的项目目录下创建一个vcpkg.json{ name: my-awesome-app, version: 1.0.0, dependencies: [ spdlog, { name: fmt, version: 9.0.0 } ] }然后在配置 CMake 时除了指定工具链文件还需要开启清单模式cmake -B build -DCMAKE_TOOLCHAIN_FILED:/Dev/vcpkg/scripts/buildsystems/vcpkg.cmake -DVCPKG_MANIFEST_MODEONvcpkg会读取项目根目录的vcpkg.json自动安装其中声明的依赖项到一个项目本地的vcpkg_installed目录而不是全局的installed目录。这样做的好处是版本隔离每个项目可以使用不同版本的同一个库互不干扰。依赖可重现清单文件可以加入版本控制确保所有开发者和构建服务器使用完全一致的依赖版本。干净的环境项目删除后其依赖也随之清理不会污染全局环境。3.3 安装后的验证与基本使用安装完spdlog后如何验证它是否可用最快的方法是写一个简单的测试程序。创建一个test_spdlog.cpp文件#include spdlog/spdlog.h #include spdlog/sinks/basic_file_sink.h int main() { // 1. 创建控制台日志器默认 auto console_logger spdlog::default_logger(); console_logger-info(Welcome to spdlog!这是一个中文测试。); console_logger-error(Some error message with arg: {}, 1); // 2. 创建文件日志器 try { auto file_logger spdlog::basic_logger_mt(file_logger, logs/basic-log.txt); file_logger-info(This log message will be written to a file.); } catch (const spdlog::spdlog_ex ex) { spdlog::error(Log init failed: {}, ex.what()); } // 3. 设置全局日志级别 spdlog::set_level(spdlog::level::debug); // 只有级别 debug 的日志才会被输出 spdlog::debug(This is a debug message which will be shown now.); // 4. 修改日志模式同步 vs 异步 spdlog::info(Default is synchronous logging.); // 异步日志配置通常在创建logger时指定后面会详述 spdlog::drop_all(); // 在程序结束前释放所有日志器资源 return 0; }编译与运行如果你使用了vcpkg integrate install直接用 Visual Studio 创建一个新的控制台项目把这个代码粘贴进去编译运行即可。VS 会自动找到头文件和链接库。如果你使用 CMake创建一个CMakeLists.txtcmake_minimum_required(VERSION 3.15) project(SpdlogTest) find_package(spdlog CONFIG REQUIRED) # 或者使用更通用的方式如果spdlog提供了Config模块 # find_package(spdlog REQUIRED) add_executable(test_spdlog test_spdlog.cpp) target_link_libraries(test_spdlog PRIVATE spdlog::spdlog)然后在项目目录下使用我们之前提到的 CMake 命令带上工具链文件参数进行配置和构建。你会发现find_package(spdlog CONFIG REQUIRED)能够成功找到通过vcpkg安装的spdlog这就是工具链文件在起作用。运行程序你会在控制台看到彩色输出的日志同时在项目目录下生成一个logs文件夹里面包含basic-log.txt文件。这证明spdlog已经成功安装并可以正常工作。4.spdlog核心功能深度解析与实战技巧通过vcpkg轻松获取spdlog后我们来深入挖掘一下这个日志库的强大之处。它远不止是简单的printf替代品。4.1 日志器、接收器与格式化器核心三要素spdlog的架构非常清晰围绕三个核心概念构建日志器你直接交互的对象用于产生日志。一个日志器可以关联多个接收器。接收器决定日志的输出目的地。例如控制台、文件、网络、系统日志等。spdlog内置了十几种接收器。格式化器控制日志消息的最终呈现格式。你可以自定义时间格式、日志级别显示、进程ID、线程ID等信息。创建自定义日志器#include spdlog/spdlog.h #include spdlog/sinks/stdout_color_sinks.h #include spdlog/sinks/rotating_file_sink.h // 支持文件回滚的接收器 #include spdlog/async.h // 异步日志 int main() { // 创建两个接收器彩色控制台 和 回滚文件 auto console_sink std::make_sharedspdlog::sinks::stdout_color_sink_mt(); auto file_sink std::make_sharedspdlog::sinks::rotating_file_sink_mt(myapp.log, 1024 * 1024 * 5, 3); // 最大5MB保留3个备份 // 设置接收器各自的日志级别 console_sink-set_level(spdlog::level::info); file_sink-set_level(spdlog::level::debug); // 文件记录更详细的debug信息 // 创建一个日志器同时拥有这两个接收器 std::vectorspdlog::sink_ptr sinks{console_sink, file_sink}; auto combined_logger std::make_sharedspdlog::logger(multi_sink, sinks.begin(), sinks.end()); combined_logger-set_level(spdlog::level::debug); // 日志器自身的级别是过滤的总闸 // 注册为全局日志器方便在任何地方使用 spdlog::register_logger(combined_logger); spdlog::set_default_logger(combined_logger); // 现在使用全局默认日志器记录 spdlog::info(This goes to both console and file.); spdlog::debug(This debug message goes to file only, because console level is info.); // 也可以直接使用命名的日志器 if(auto logger spdlog::get(multi_sink)) { logger-warn(Retrieved logger by name.); } return 0; }这个例子展示了如何灵活组合接收器并为不同输出目的地设置不同的日志级别这是实际项目中非常实用的模式。4.2 异步日志性能关键场景的救星默认情况下spdlog的日志记录是同步的。这意味着每次调用logger-info(...)时程序都会阻塞等待该条日志完全写入接收器如文件后才继续执行。对于高频日志或性能敏感的应用这可能会成为瓶颈。spdlog提供了强大的异步日志功能。它内部维护一个全局的线程池和消息队列。当使用异步模式时日志调用会立刻将消息放入队列后返回由后台线程负责实际的写入操作。启用全局异步日志#include spdlog/async.h #include spdlog/sinks/basic_file_sink.h #include spdlog/sinks/rotating_file_sink.h int main() { // 关键步骤1设置异步日志的全局线程池参数 // 队列大小8192条消息后台线程数1如果队列满新日志将阻塞非丢弃 spdlog::init_thread_pool(8192, 1); // 队列大小线程数 // 关键步骤2使用异步工厂函数创建接收器 // 注意接收器本身需要是线程安全的如 basic_file_sink_mt 或 rotating_file_sink_mt auto async_file_sink std::make_sharedspdlog::sinks::basic_file_sink_mt(async_log.txt); // 关键步骤3使用 spdlog::async_logger 创建异步日志器 auto async_logger std::make_sharedspdlog::async_logger(async_logger, async_file_sink, spdlog::thread_pool(), spdlog::async_overflow_policy::block); async_logger-set_level(spdlog::level::info); spdlog::set_default_logger(async_logger); // 现在日志调用是非阻塞的 for(int i 0; i 100000; i) { spdlog::info(Async log message #{}, i); // 这行执行很快不会阻塞 } // 程序结束前必须显式刷新并关闭异步日志器确保所有队列中的日志被写出 spdlog::shutdown(); return 0; }异步日志的注意事项溢出策略spdlog::async_overflow_policy::block表示队列满时阻塞生产者你的主线程这是最安全的选择确保不丢日志。另一个选项是overrun_oldest会丢弃最老的日志适用于对实时性要求高于完整性的场景。性能权衡异步日志极大提升了主线程的响应速度但增加了内存开销队列和潜在的延迟日志并非实时写入。对于绝大多数应用异步日志带来的收益远大于开销。关闭顺序必须调用spdlog::shutdown()来确保后台线程完成工作并退出否则程序退出时可能丢失最后一部分日志。4.3 高级格式化与自定义模式spdlog默认的日志格式已经很美观但你完全可以自定义。格式化模式字符串类似于printf的格式说明符但功能更强大。#include spdlog/spdlog.h #include spdlog/pattern_formatter.h int main() { auto logger spdlog::default_logger(); // 1. 设置自定义格式 // %Y-%m-%d %H:%M:%S.%e: 带毫秒的完整时间 // %l: 日志级别 (info, error等) // %n: 日志器名称 // %t: 线程ID // %v: 实际的日志消息 // %: 源文件和行号需要定义 SPDLOG_ACTIVE_LEVEL 并启用 logger-set_pattern([%Y-%m-%d %H:%M:%S.%e] [%^%l%$] [thread %t] [%n] %v); logger-info(This message has a custom format with thread ID.); // 2. 为不同接收器设置不同格式 auto console_sink std::make_sharedspdlog::sinks::stdout_color_sink_mt(); auto file_sink std::make_sharedspdlog::sinks::basic_file_sink_mt(formatted.log); console_sink-set_pattern(%^[%H:%M:%S] [%l]%$ %v); // 控制台用简洁彩色格式 file_sink-set_pattern([%Y-%m-%d %H:%M:%S.%e] [%l] [tid:%t] %v); // 文件用详细格式 auto dual_logger std::make_sharedspdlog::logger(format_demo, spdlog::sinks_init_list{console_sink, file_sink}); dual_logger-info(This will appear in console (colored, simple) and file (detailed).); // 3. 使用 fmtlib 的强大格式化功能spdlog 内部集成 fmt int id 42; std::string name Alice; double value 3.14159; logger-info(User info: id{}, name{}, score{:.2f}, id, name, value); // 支持浮点数精度控制 logger-info(Hex: 0x{:x}, Scientific: {:.3e}, 255, value); return 0; }通过灵活的组合你可以让控制台输出简洁明了便于调试同时让文件日志记录详尽的信息便于事后分析。5.vcpkg高级用法、问题排查与生态融入5.1 镜像加速与自定义端口镜像加速是提升国内使用体验的关键。vcpkg的下载源主要是 GitHub速度不稳定。我们可以通过配置来使用镜像。设置下载缓存设置环境变量VCPKG_DOWNLOADS指向一个本地目录vcpkg会将下载的源码包缓存于此下次安装相同版本时无需重复下载。使用镜像服务器修改vcpkg的配置文件。在vcpkg安装目录下创建或修改vcpkg-configuration.json文件{ default-registry: { kind: git, repository: https://gitee.com/vcpkg/vcpkg, // 例如使用 Gitee 镜像 baseline: a1c8f1c6c7c80a8c2e4b2c2f7f2c2f7f2c2f7f2c }, registries: [ { kind: artifact, location: https://github.com/microsoft/vcpkg-ce-catalog/archive/refs/heads/main.zip, name: microsoft } ] }请注意镜像地址和基线提交哈希需要从可靠的社区镜像站获取并注意其更新是否及时。基线哈希用于锁定“食谱”集合的版本确保可重现性。自定义端口与覆盖有时你需要一个vcpkg官方尚未收录的库或者需要修改某个已有库的编译选项。这时可以使用“覆盖端口”功能。在你的项目目录下创建一个vcpkg-overlays文件夹。在里面仿照vcpkg/ports/portname的结构创建你自己的端口目录包含portfile.cmake和vcpkg.json。在项目的vcpkg-configuration.json中指定覆盖路径{ overlay-ports: [./vcpkg-overlays] }这样vcpkg在查找库时会优先使用你项目中的端口定义。这是应对特殊依赖需求的终极武器。5.2 常见问题与排查实录即使有vcpkg这样的利器在实际使用中依然会遇到各种问题。下面是我总结的一些常见坑点及解决方案。问题1安装失败提示 “Building package … failed”这是最常见的问题通常是由于编译依赖缺失或网络问题。排查步骤看完整错误日志vcpkg的错误信息通常很长滚动到最顶部找到第一个CMake Error或error:开头的行那才是根源。检查依赖错误信息常会提示缺少某个工具如nasm,perl,bison等。你需要手动安装这些构建工具并确保它们在系统的PATH中。对于 Windows一个常见的解决方案是安装MSYS2或Cygwin并将其usr/bin目录加入PATH。检查 Visual Studio 组件确保安装了 “使用 C 的桌面开发” 工作负载并且包含了 “Windows 10 SDK” 和 “MSVC v143 … 生成工具”。有时需要特定版本的 Windows SDK。尝试清理重试使用vcpkg remove package移除失败的包然后vcpkg install package --recurse重新安装。--recurse会强制重新下载和编译所有依赖。网络问题如果是下载超时尝试配置镜像源或使用代理注意合规性。问题2CMake 的find_package找不到通过vcpkg安装的库可能原因1没有正确传递CMAKE_TOOLCHAIN_FILE参数。这是最可能的原因。务必在第一次配置 CMake 项目时就指定该参数。如果已经配置过但没有指定需要删除build目录从头再来。可能原因2库的 CMake 配置文件名称不匹配。vcpkg安装的库其 CMake 配置文件名称可能和find_package中使用的不同。例如spdlog可以通过find_package(spdlog CONFIG REQUIRED)找到但有些库可能需要全小写或特定名称。查看vcpkg安装目录下installed/triplet/share/package-name里的.cmake文件确认正确的包名。可能原因3三元组不匹配。如果你用vcpkg install spdlog:x64-windows-static安装的静态库但在 CMake 中想用动态链接就可能找不到。确保安装的三元组与你的项目目标一致。问题3链接错误如 “LNK2005: 符号已定义” 或 “LNK2019: 无法解析的外部符号”可能原因1运行时库冲突。这是 Windows 上经典的/MTvs/MD问题。如果你用vcpkg install spdlog:x64-windows动态链接安装的库但你的项目属性中设置了/MT静态链接运行时库就会导致链接冲突。解决方案是统一要么全部用动态/MD对应x64-windows要么全部用静态/MT对应x64-windows-static。可能原因2没有正确链接依赖项。虽然vcpkg integrate和工具链文件能自动处理很多链接但对于复杂的库有时仍需在CMakeLists.txt中明确链接其依赖。例如如果spdlog使用了fmt而你的代码直接用了fmt的功能你可能也需要target_link_libraries(myapp PRIVATE fmt::fmt)。问题4spdlog异步日志在程序退出时丢失最后几条日志原因程序退出时日志队列中的消息可能还没来得及被后台线程写出进程就结束了。解决方案在main函数返回前或任何可能导致进程退出的地方如异常处理中调用spdlog::shutdown()。这会刷新所有日志器并等待后台线程结束。对于异步日志这是必须的步骤。5.3 将vcpkgspdlog融入现代 C 工作流最后我们来谈谈如何将这套工具链优雅地融入一个现代的、团队协作的 C 项目中。假设我们有一个使用 CMake 管理的项目MyProject。项目结构示例MyProject/ ├── CMakeLists.txt # 主 CMake 文件 ├── vcpkg.json # 项目依赖清单 ├── vcpkg-configuration.json # vcpkg 配置如镜像 ├── src/ │ ├── CMakeLists.txt │ └── main.cpp ├── include/ └── build/ # 构建输出目录.gitignorevcpkg.json(依赖声明):{ $schema: https://raw.githubusercontent.com/microsoft/vcpkg/master/scripts/vcpkg.schema.json, name: myproject, version: 0.1.0, dependencies: [ { name: spdlog, features: [fmt] // 显式启用 fmt 功能如果需要使用 fmt 的格式化 }, fmt // 你也可以直接依赖 fmt如果你需要直接使用它 ] }CMakeLists.txt(简化版):cmake_minimum_required(VERSION 3.15) project(MyProject LANGUAGES CXX) # 关键在 project() 之后任何 find_package 之前设置工具链文件。 # 通常通过命令行参数 -DCMAKE_TOOLCHAIN_FILE... 传入这里只是说明。 # set(CMAKE_TOOLCHAIN_FILE ${CMAKE_CURRENT_SOURCE_DIR}/vcpkg/scripts/buildsystems/vcpkg.cmake CACHE STRING ) find_package(spdlog CONFIG REQUIRED) find_package(fmt CONFIG REQUIRED) # 可选如果你直接使用 fmt add_executable(myapp src/main.cpp) target_link_libraries(myapp PRIVATE spdlog::spdlog_header_only # 如果使用纯头文件模式 # 或者 spdlog::spdlog # 如果使用编译模式 fmt::fmt ) # 设置 C 标准 target_compile_features(myapp PRIVATE cxx_std_17)开发与构建流程新成员克隆项目代码。在项目根目录执行 CMake 配置命令启用清单模式和指定工具链cmake -B build -DCMAKE_TOOLCHAIN_FILE[你的vcpkg路径]/scripts/buildsystems/vcpkg.cmake -DVCPKG_MANIFEST_MODEONCMake 会自动调用vcpkg根据vcpkg.json安装所有依赖到build/vcpkg_installed。编译项目cmake --build build --config Release。整个过程无需手动运行vcpkg install依赖管理完全自动化、可重现。这套流程将vcpkg从“一个好用的工具”升级为“项目基础设施的一部分”。它确保了依赖的版本一致性简化了开发环境搭建让开发者能更专注于代码本身。而spdlog作为通过vcpkg轻松获取的高质量组件则为项目提供了稳定、高性能的日志能力是现代 C 项目日志方案的一个非常可靠的选择。

相关新闻