CMake 生成静态库、动态库

在 CMake 中,生成静态库(Static Library)或动态库(Shared Library)非常简单。CMake 提供了 add_library 命令来定义库文件,并通过参数指定库的类型(静态库或动态库)。以下是详细的步骤和示例:


1. 生成静态库

静态库在编译时会被完整地链接到可执行文件中,生成的文件扩展名通常为 .lib(Windows)或 .a(Linux/macOS)。

示例代码
cmake_minimum_required(VERSION 3.10)
project(MyLibraryProject)

# 添加静态库
add_library(MyStaticLibrary STATIC src/utils.cpp)

# 设置静态库的输出目录
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib)
说明
  • add_library(MyStaticLibrary STATIC src/utils.cpp)
    • MyStaticLibrary 是库的名称。
    • STATIC 表示生成静态库。
    • src/utils.cpp 是库的源文件。
  • CMAKE_ARCHIVE_OUTPUT_DIRECTORY:用于设置静态库的输出目录。

2. 生成动态库

动态库在运行时被加载,生成的文件扩展名通常为 .dll(Windows)或 .so(Linux/macOS)。

示例代码
cmake_minimum_required(VERSION 3.10)
project(MyLibraryProject)

# 添加动态库
add_library(MySharedLibrary SHARED src/utils.cpp)

# 设置动态库的输出目录
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib)
说明
  • add_library(MySharedLibrary SHARED src/utils.cpp)
    • MySharedLibrary 是库的名称。
    • SHARED 表示生成动态库。
    • src/utils.cpp 是库的源文件。
  • CMAKE_LIBRARY_OUTPUT_DIRECTORY:用于设置动态库的输出目录。

3. 同时生成静态库和动态库

如果需要同时生成静态库和动态库,可以定义两个不同的目标:

示例代码
cmake_minimum_required(VERSION 3.10)
project(MyLibraryProject)

# 添加静态库
add_library(MyStaticLibrary STATIC src/utils.cpp)

# 添加动态库
add_library(MySharedLibrary SHARED src/utils.cpp)

# 设置输出目录
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib) # 静态库
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib) # 动态库

4. 设置库的版本和导出符号

对于动态库,通常需要设置版本号和导出符号。

示例代码
cmake_minimum_required(VERSION 3.10)
project(MyLibraryProject)

# 添加动态库
add_library(MySharedLibrary SHARED src/utils.cpp)

# 设置库的版本号
set_target_properties(MySharedLibrary PROPERTIES
    VERSION 1.0.0
    SOVERSION 1
)

# 导出符号(Windows 下需要)
if (WIN32)
    target_compile_definitions(MySharedLibrary PRIVATE MYSHAREDLIBRARY_EXPORTS)
endif()
说明
  • VERSIONSOVERSION:用于设置库的版本号。
  • target_compile_definitions:在 Windows 下,通常需要导出符号(通过 __declspec(dllexport))。

5. 链接库文件

生成库文件后,可以在其他目标中链接这些库。

示例代码
cmake_minimum_required(VERSION 3.10)
project(MyProject)

# 添加可执行文件
add_executable(MyProgram main.cpp)

# 链接静态库
target_link_libraries(MyProgram MyStaticLibrary)

# 或者链接动态库
target_link_libraries(MyProgram MySharedLibrary)

6. 完整示例

以下是一个完整的示例,展示如何生成静态库和动态库,并在可执行文件中链接它们:

cmake_minimum_required(VERSION 3.10)
project(MyLibraryProject)

# 设置输出目录
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib) # 静态库
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib) # 动态库
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin) # 可执行文件

# 添加静态库
add_library(MyStaticLibrary STATIC src/utils.cpp)

# 添加动态库
add_library(MySharedLibrary SHARED src/utils.cpp)

# 设置动态库的版本号
set_target_properties(MySharedLibrary PROPERTIES
    VERSION 1.0.0
    SOVERSION 1
)

# 添加可执行文件
add_executable(MyProgram main.cpp)

# 链接静态库
target_link_libraries(MyProgram MyStaticLibrary)

# 或者链接动态库
target_link_libraries(MyProgram MySharedLibrary)

7. 构建项目

在项目根目录下运行以下命令来构建项目:

mkdir build
cd build
cmake ..
cmake --build .

构建完成后:

  • 静态库会生成在 build/lib/ 目录下(如 libMyStaticLibrary.aMyStaticLibrary.lib)。
  • 动态库会生成在 build/lib/ 目录下(如 libMySharedLibrary.soMySharedLibrary.dll)。
  • 可执行文件会生成在 build/bin/ 目录下。

总结

  • 使用 add_library 生成静态库(STATIC)或动态库(SHARED)。
  • 通过 CMAKE_ARCHIVE_OUTPUT_DIRECTORYCMAKE_LIBRARY_OUTPUT_DIRECTORY 设置库的输出目录。
  • 使用 target_link_libraries 链接库文件到可执行文件。
  • 动态库可以设置版本号和导出符号(特别是在 Windows 下)。
### 使用CMake生成动态库静态库C++开发过程中,通过CMake可以方便地管理项目并生成不同类型的库文件。为了创建动态库(共享库)和静态库,可以在`CMakeLists.txt`中定义相应的设置。 #### 创建静态库 静态库是在编译阶段链接到目标程序中的二进制文件集合。要创建一个名为`my_static_lib`的静态库: ```cmake add_library(my_static_lib STATIC src/static.cpp) ``` 这条命令告诉CMake将指定源码文件打包成静态库[^1]。 对于更复杂的场景,比如处理头文件复制以及解决多重包涵依赖关系时,则可参照如下配置方式来增强构建脚本的功能性[^3]: ```cmake set(header_files "path/to/header.h") file(COPY ${header_files} DESTINATION ${PROJECT_BINARY_DIR}/out/include) target_include_directories(my_static_lib PUBLIC ${PROJECT_SOURCE_DIR}/include) ``` 这里不仅指定了静态库本身的信息,还设置了公共包含路径以便其他模块能够访问该库提供的接口。 #### 创建动态库 相比之下,动态库会在运行时加载,并允许多个应用程序共享同一份副本。以下是创建名为`my_shared_lib`的动态库的方法: ```cmake add_library(my_shared_lib SHARED src/shared.cpp) ``` 此指令会指示CMake按照平台约定的方式去生产共享对象(.so) 或者DLL (.dll),具体取决于操作系统环境。 当涉及到多层依赖项之间的相互作用时——特别是针对那些既含有内部又存在外部依赖性的大型工程来说,在链接选项上做适当调整就显得尤为重要了: ```cmake set(LIBS "-L/path/to/libraries -llibrary_name") target_link_libraries(my_shared_lib PRIVATE -Wl,--start-group ${LIBS} -Wl,--end-group) ``` 上述代码片段展示了如何利用特定于链接器的关键字参数(`-Wl`) 来确保所有必要的符号都能被正确解析出来。 综上所述,无论是静态还是动态库的制作过程都离不开合理规划好各个组成部分间的关联逻辑;而借助像CMake这样的工具则可以让整个流程变得更加高效便捷。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值