CLion编译和使用动态库

1. 使用Clion 开发动态库文件

1.1 动态库简介

注意:在 linux 平台下,动态库和静态库的源代码是完全一样的,只需要修改编译参数即可。在 Windows 平台中生成动态库其源码和静态库是不同的。

在 Windows 平台中,我们导出动态库时,除了会生成 .dll 动态库之外还会生成一个 .lib 文件。这个 .lib 文件和静态库的 .lib 文件不同,它里面并不保存代码生成的二进制文件,而是所有需要导出符号的符号表。因此这个 .lib 文件和编译静态库生成的 .lib 文件相比会小很多。而这个导出的符号表是需要我们在源码中进行指定的。如果我们希望将将一个符号(symbol)导出(这里的符号可以指类、函数等各种类型),需要在其前面加上 __declspec(dllexport) 标志。这样这个符号的相关信息就会导出的 .lib 中的符号表中了。如果我们的源码中没有任何 __declspec(dllexport) 的话,我们依然可以成功的编译出动态库,但是并不会生成保存符号表的.lib 文件。这也是在 Windows 平台下编译动态库经常出现的问题,如果我们的源码是在 Linux 平台下编写的话,更是很容易忘记修改源码。

原文链接:https://blog.youkuaiyun.com/Snow__Sunny/article/details/123182732

如上所述,windows下的动态库源代码要实现跨平台的特性就会比较麻烦,不过好在cmake有自己的解决方法,知道原理是啥就行。

1.2 新建Library项目

在这里插入图片描述

1.3 CmakeLists.txt的设置

GenerateExportHeader — CMake 3.24.0-rc3 Documentation

cmake_minimum_required(VERSION 3.22)
set(CMAKE_CXX_STANDARD 14)

project(MyDLL)

# 导入 GenerateExportHeader 函数
include(GenerateExportHeader)
#set(CMAKE_CXX_VISIBILITY_PRESET hidden)
#set(CMAKE_VISIBILITY_INLINES_HIDDEN 1)

# 判断是否是debug模式,如果是debug,则后缀加‘d',比如 MyDLLd.dll MyDLLd.lib
set(DEBUG_SUFFIX)
if (MSVC AND CMAKE_BUILD_TYPE MATCHES "Debug")
    set(DEBUG_SUFFIX "d")
endif ()
# CMAKE_DEBUG_POSTFIX 全局变量用于附加 d对于调试库:
set(CMAKE_DEBUG_POSTFIX d)

# 定义目标名称变量
set(TargetName ${PROJECT_NAME})
message(${TargetName})
# 生成 动态的 MyDLL.dll 文件
add_library(${TargetName} SHARED library.cpp)
# MyDLL export宏定义, 生成的文件名为 mydll_export.h, 路径: ${PROJECT_BINARY_DIR}
GENERATE_EXPORT_HEADER(${TargetName})
INCLUDE_DIRECTORIES(${PROJECT_BINARY_DIR})

# 设置安装目录
SET(CMAKE_INSTALL_PREFIX ${PROJECT_BINARY_DIR}/${PROJECT_NAME}_lib)
# 拷贝头文件 到 include 目录下
INSTALL(FILES library.h ${PROJECT_BINARY_DIR}/mydll_export.h  DESTINATION include)
# 将 dll 和 lib 库文件 分别放到 lib 和 bin 目录下
INSTALL(TARGETS ${TargetName} LIBRARY DESTINATION lib)

Reload Cmake Project 后,在项目的二进制目录下自动生成mydll_export.h

在这里插入图片描述

1.4 ABI文件导入mydll_export.h

导入头文件后,并使用MYDLL_EXPORT 声明到处的函数

在这里插入图片描述

1.5 构建项目

构建项目执行后,会生成相关的库文件,如下图所示:
在这里插入图片描述

1.6 安装

点击Install后,会自动将库文件放到相应的目录下

在这里插入图片描述

2. 使用第三方动态库文件

动态库就使用生成的MyDLL

2.1 新建项目

在这里插入图片描述

2.2 复制MyDLL库文件到源代码目录

在这里插入图片描述

2.3 CmakeLists.txt的设置

cmake_minimum_required(VERSION 3.22)
project(UseDLL)

set(CMAKE_CXX_STANDARD 14)
# 判断是否是debug模式,如果是debug,则后缀加‘d',比如 MyDLLd.dll MyDLLd.lib
set(DEBUG_SUFFIX)
if (MSVC AND CMAKE_BUILD_TYPE MATCHES "Debug")
    set(DEBUG_SUFFIX "d")
endif ()
# CMAKE_DEBUG_POSTFIX 全局变量用于附加 d对于调试库:
#set(CMAKE_DEBUG_POSTFIX d)  # 这玩意在使用库文件的时候,似乎没有用处


add_executable(UseDLL main.cpp)
#INCLUDE_DIRECTORIES(MyDLL_lib/include)  # 这种方式也可以导入库文件

# 为目标添加 include 目录
target_include_directories(UseDLL
        PUBLIC
        ${PROJECT_SOURCE_DIR}/MyDLL_lib/include)

message(${PROJECT_SOURCE_DIR}/MyDLL_lib/lib/MyDLL${DEBUG_SUFFIX})

# 为目标 链接添加 lib文件
target_link_libraries(UseDLL
        PRIVATE
        ${PROJECT_SOURCE_DIR}/MyDLL_lib/lib/MyDLL${DEBUG_SUFFIX}.lib)
# 这种用目录的方式处理的不是很好,需要明确指定到lib的文件名,应该有其他的方式

2.4 使用库中的头文件

在这里插入图片描述

2.5 编译运行

将dll文件复制到二进制目录,然后编译运行即可

在这里插入图片描述

顺利打印出“hello,World!”

### CLion 编译可执行文件并正确链接库 为了使CLion编译的可执行文件能够正确链接库,需确保项目的`CMakeLists.txt`配置无误。具体来说: #### 1. 设置项目基本信息 在`CMakeLists.txt`中指定最低版本要求项目名称。 ```cmake cmake_minimum_required(VERSION 3.10) project(MyProject CXX) ``` #### 2. 查找并引入所需库 对于像OpenCV这样的第三方库,应通过`find_package()`命令来查找其安装位置,并设置相应的头文件路径与库目录。 ```cmake find_package(OpenCV REQUIRED) include_directories(${OpenCV_INCLUDE_DIRS}) ``` 这一步骤确保了编译器知道去哪里寻找必要的头文件[^3]。 #### 3. 添加源文件到目标 定义要构建的目标(如可执行文件),并将所有相关的`.cpp`或其他类型的源码加入其中。 ```cmake add_executable(myapp main.cpp other_source_file.cpp) ``` #### 4. 进行静态或动态链接 为了让应用程序能够在运行时找到所需的共享对象(例如Windows下的DLLs),需要显式地告诉CMake哪些库应该被链接进来。 ```cmake target_link_libraries(myapp ${OpenCV_LIBS} pthread dl rt m) ``` 上述代码片段不仅包含了来自OpenCV的具体实现细节,还额外加入了几个常用的Linux系统级库;而在Windows平台上,则可能只需要关注于特定的应用场景所必需的部分即可[^2]。 #### 5. 解决依赖项问题 当存在跨模块间的相互引用时,务必保证各个组件之间的顺序合理,避免循环依赖等问题的发生。可以通过调整`target_include_directories()`等指令来进行优化处理。 #### 6. 处理平台差异 考虑到不同操作系统间可能存在细微差别,在编写跨平台应用时建议采用条件判断语句区分对待各种情况。 ```cmake if(MINGW OR MSYS OR CYGWIN) set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -static-libgcc") endif() ``` 此段脚本专门针对MinGW环境做了特殊处理,解决了因缺少libgcc而导致无法正常启动的问题[^1]。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值