news 2026/7/27 20:22:11

CMake构建学习笔记-SQLite库的构建

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
CMake构建学习笔记-SQLite库的构建

CMake构建学习笔记-SQLite库的构建

一、CMake与SQLite基础概念### 1.1 什么是CMake?CMake是一个跨平台的构建工具,它通过CMakeLists.txt文件描述项目的构建过程,并生成对应平台的Makefile或项目文件(如Visual Studio解决方案)。相比直接编写Makefile,CMake提供了更简洁、可移植的构建方案,特别适合管理依赖关系复杂的C/C++项目。### 1.2 什么是SQLite?SQLite是一个轻量级的嵌入式关系数据库引擎,它不需要独立的服务器进程,数据直接存储在单个磁盘文件中。SQLite的源代码是C语言编写的,在嵌入式系统、移动应用和桌面软件中广泛使用。### 1.3 为什么要用CMake构建SQLite?SQLite官方手册推荐直接包含其源代码文件(sqlite3.csqlite3.h)到项目中,但这种方式在大型项目或需要跨平台编译时存在弊端:- 缺乏灵活的编译选项控制(如线程安全、内存分配器)- 难以集成到现代CMake项目的依赖管理流程中- 不利于版本管理和自动化构建通过CMake构建SQLite库,可以:- 使用CMake的option命令控制编译特性- 自动处理平台差异- 生成可复用的库文件(静态库或动态库)—## 二、从零开始构建SQLite库### 2.1 准备工作首先,从SQLite官网下载源代码包(sqlite-amalgamation-3450200.zip),解压后得到以下核心文件:-sqlite3.c:合并后的SQLite实现-sqlite3.h:头文件-sqlite3ext.h:扩展接口头文件(可选)### 2.2 创建基础的CMakeLists.txt在解压目录下创建CMakeLists.txt文件,这是CMake构建的核心:cmake# CMakeLists.txt - 基础版本cmake_minimum_required(VERSION 3.10)project(SQLite3 VERSION 3.45.2 LANGUAGES C)# 定义库目标:从单个源文件编译静态库add_library(sqlite3 STATIC sqlite3.c)# 指定头文件路径(当前目录)target_include_directories(sqlite3 PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})# 启用线程安全支持(默认开启)target_compile_definitions(sqlite3 PRIVATE SQLITE_THREADSAFE=1 # 1表示线程安全,0表示单线程)# 设置输出目录set_target_properties(sqlite3 PROPERTIES ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib)### 2.3 构建与测试在终端中执行以下命令:bashmkdir build && cd buildcmake ..cmake --build . --config Release构建成功后,会在build/lib目录下生成libsqlite3.a(Linux)或sqlite3.lib(Windows)。—## 三、高级用法:定制编译选项### 3.1 为什么需要定制选项?SQLite提供了大量编译时选项来优化不同场景:-SQLITE_DEFAULT_CACHE_SIZE:默认缓存大小-SQLITE_ENABLE_FTS5:启用全文搜索-SQLITE_OMIT_LOAD_EXTENSION:禁用扩展加载### 3.2 增强版CMakeLists.txt以下代码展示了如何使用CMake的option命令暴露编译选项:cmake# CMakeLists.txt - 高级版本cmake_minimum_required(VERSION 3.15)project(SQLite3 VERSION 3.45.2 LANGUAGES C)# ========== 编译选项 ==========option(SQLITE_ENABLE_THREADS "启用线程安全" ON) # 默认开启option(SQLITE_ENABLE_FTS5 "启用全文搜索5" OFF) # 默认关闭option(SQLITE_OMIT_LOAD_EXTENSION "禁用扩展加载" OFF) # 默认允许加载# ========== 库目标定义 ==========add_library(sqlite3 STATIC sqlite3.c)target_include_directories(sqlite3 PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})# ========== 条件编译定义 ==========# 根据选项添加预处理器定义if(SQLITE_ENABLE_THREADS) target_compile_definitions(sqlite3 PRIVATE SQLITE_THREADSAFE=1)else() target_compile_definitions(sqlite3 PRIVATE SQLITE_THREADSAFE=0)endif()if(SQLITE_ENABLE_FTS5) target_compile_definitions(sqlite3 PRIVATE SQLITE_ENABLE_FTS5)endif()if(SQLITE_OMIT_LOAD_EXTENSION) target_compile_definitions(sqlite3 PRIVATE SQLITE_OMIT_LOAD_EXTENSION)endif()# ========== 输出配置 ==========set_target_properties(sqlite3 PROPERTIES ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib # 设置C标准(SQLite需要C99以上) C_STANDARD 99 C_STANDARD_REQUIRED ON)# ========== 安装规则(可选) ==========install(TARGETS sqlite3 ARCHIVE DESTINATION lib LIBRARY DESTINATION lib)install(FILES sqlite3.h sqlite3ext.h DESTINATION include)### 3.3 使用自定义选项构建现在可以通过-D参数控制编译特性:bashmkdir build_fts5 && cd build_fts5cmake .. -DSQLITE_ENABLE_FTS5=ON -DSQLITE_ENABLE_THREADS=OFFcmake --build .这样生成的库将包含FTS5全文搜索功能,但禁用线程安全。—## 四、集成SQLite到其他项目### 4.1 作为外部依赖使用创建另一个项目MyApp,在它的CMakeLists.txt中引用SQLite库:cmake# MyApp/CMakeLists.txtcmake_minimum_required(VERSION 3.10)project(MyApp LANGUAGES CXX)# 指定SQLite库路径set(SQLITE3_DIR "../sqlite3-build" CACHE PATH "SQLite3构建目录")# 导入已构建的库add_library(sqlite3 STATIC IMPORTED)set_target_properties(sqlite3 PROPERTIES IMPORTED_LOCATION ${SQLITE3_DIR}/lib/libsqlite3.a INTERFACE_INCLUDE_DIRECTORIES ${SQLITE3_DIR}/../sqlite3-src)# 创建应用程序目标add_executable(myapp main.cpp)# 链接SQLitetarget_link_libraries(myapp PRIVATE sqlite3)### 4.2 验证集成的C++示例创建main.cpp测试数据库操作:cpp// main.cpp - 测试SQLite数据库操作#include <iostream>#include <sqlite3.h>int main() { sqlite3* db = nullptr; char* errMsg = nullptr; // 1. 打开数据库(如果不存在则创建) int rc = sqlite3_open("test.db", &db); if (rc != SQLITE_OK) { std::cerr << "无法打开数据库: " << sqlite3_errmsg(db) << std::endl; return 1; } // 2. 创建表 const char* createSQL = "CREATE TABLE IF NOT EXISTS users (" " id INTEGER PRIMARY KEY AUTOINCREMENT," " name TEXT NOT NULL," " age INTEGER" ");"; rc = sqlite3_exec(db, createSQL, nullptr, nullptr, &errMsg); if (rc != SQLITE_OK) { std::cerr << "SQL错误: " << errMsg << std::endl; sqlite3_free(errMsg); } else { std::cout << "表创建成功" << std::endl; } // 3. 插入数据 const char* insertSQL = "INSERT INTO users (name, age) VALUES ('张三', 25);"; rc = sqlite3_exec(db, insertSQL, nullptr, nullptr, &errMsg); if (rc != SQLITE_OK) { std::cerr << "插入失败: " << errMsg << std::endl; sqlite3_free(errMsg); } // 4. 查询数据 sqlite3_stmt* stmt = nullptr; const char* querySQL = "SELECT id, name, age FROM users;"; rc = sqlite3_prepare_v2(db, querySQL, -1, &stmt, nullptr); if (rc == SQLITE_OK) { while (sqlite3_step(stmt) == SQLITE_ROW) { int id = sqlite3_column_int(stmt, 0); const char* name = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 1)); int age = sqlite3_column_int(stmt, 2); std::cout << "用户: id=" << id << ", 姓名=" << name << ", 年龄=" << age << std::endl; } } sqlite3_finalize(stmt); // 5. 关闭数据库 sqlite3_close(db); std::cout << "数据库操作完成" << std::endl; return 0;}—## 五、总结通过本文的学习,我们掌握了使用CMake构建SQLite库的完整流程:1.基础构建:从简单的add_library开始,理解CMake构建静态库的基本模式2.选项定制:利用optiontarget_compile_definitions灵活控制SQLite的编译特性,如线程安全、全文搜索等3.跨项目集成:通过IMPORTED目标或find_package机制,将SQLite作为外部依赖引入其他项目CMake的价值在于它抽象了平台差异,让我们可以专注于项目逻辑而非构建细节。对于SQLite这样的库,使用CMake管理其构建过程,可以更高效地适配不同项目需求,同时保持构建系统的可维护性。建议读者在实际项目中尝试扩展更多编译选项(如SQLITE_ENABLE_COLUMN_METADATA),并探索使用FetchContent模块自动下载SQLite源码的现代化方式。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/7/27 20:19:35

Docker Compose健康检查与启动依赖:构建稳定测试环境的核心实践

1. 项目概述&#xff1a;为什么启动顺序是测试环境的“命门”&#xff1f;搞过微服务或者多容器应用的朋友&#xff0c;肯定对 Docker Compose 不陌生。它用一份docker-compose.yml文件&#xff0c;就把数据库、缓存、后端服务、前端应用这些“零件”组装成了一个能一键启动的“…

作者头像 李华
网站建设 2026/7/27 20:17:52

上位机智能化改造实战:用AI为PLC产线注入智能决策能力

在传统制造产线&#xff0c;PLC是绝对的控制核心&#xff0c;但绝大多数产线的PLC逻辑都是写死的硬规则&#xff1a;工艺参数固定、异常直接停机、换型靠人工逐点改参数。产线跑标准工况很稳定&#xff0c;但一旦遇到来料波动、环境变化、产品换型&#xff0c;立刻就暴露出柔性…

作者头像 李华
网站建设 2026/7/27 20:14:03

网盘直链下载助手:浏览器直连下载的终极完整教程

网盘直链下载助手&#xff1a;浏览器直连下载的终极完整教程 【免费下载链接】Online-disk-direct-link-download-assistant 一个基于 JavaScript 的网盘文件下载地址获取工具。基于【网盘直链下载助手】修改 &#xff0c;支持 百度网盘 / 阿里云盘 / 中国移动云盘 / 天翼云盘 …

作者头像 李华
网站建设 2026/7/27 20:14:00

SecHex-Spoofy 1.5.8:Windows硬件伪装工具的全面指南

SecHex-Spoofy 1.5.8&#xff1a;Windows硬件伪装工具的全面指南 【免费下载链接】SecHex-Spoofy C# HWID Changer &#x1f511;︎ Disk, Guid, Mac, Gpu, Pc-Name, Win-ID, EFI, SMBIOS Spoofing [Usermode] 项目地址: https://gitcode.com/gh_mirrors/se/SecHex-Spoofy …

作者头像 李华
网站建设 2026/7/27 20:12:40

PyTorch for Numpy users进阶:索引与切片操作的完整解析

PyTorch for Numpy users进阶&#xff1a;索引与切片操作的完整解析 【免费下载链接】pytorch-for-numpy-users PyTorch for Numpy users. https://pytorch-for-numpy-users.wkentaro.com 项目地址: https://gitcode.com/gh_mirrors/py/pytorch-for-numpy-users PyTorch…

作者头像 李华
网站建设 2026/7/27 20:11:54

网盘直链解析工具LinkSwift:打破下载速度瓶颈的完整解决方案

网盘直链解析工具LinkSwift&#xff1a;打破下载速度瓶颈的完整解决方案 【免费下载链接】Online-disk-direct-link-download-assistant 一个基于 JavaScript 的网盘文件下载地址获取工具。基于【网盘直链下载助手】修改 &#xff0c;支持 百度网盘 / 阿里云盘 / 中国移动云盘 …

作者头像 李华