“深入浅出”系列之QT:(6)如何在一个项目中调用另一个项目

在Qt中,如果想在一个项目中调用另一个项目,这通常意味着想要在一个CMake构建的项目中集成或依赖另一个CMake构建的项目。

1‌.子模块或子目录方式‌:
如果另一个项目可以作为一个子模块或子目录包含在当前项目中,可以使用add_subdirectory命令在CMake中添加它。这样,子项目的CMake配置将作为父项目配置的一部分被处理。

# 在主CMakeLists.txt中                    

 add_subdirectory(path/to/your/subproject)                                

 确保子项目有自己的CMakeLists.txt文件,并且其构建系统是与主项目兼容的。

2‌.外部项目方式(使用ExternalProject)‌:
如果子项目是一个独立的外部项目,并且你不想或不能将其源代码直接包含在你的主项目中,你可以使用CMake的ExternalProject模块来下载、配置和构建外部项目。

# 首先,你可能需要包含ExternalProject模块

include(ExternalProject)

# 然后,定义外部项目

ExternalProject_Add( external_project_name

    DOWNLOAD_DIR ${CMAKE_BINARY_DIR}/external/project_name

    SOURCE_DIR ${CMAKE_BINARY_DIR}/external/project_name/src

    BINARY_DIR ${CMAKE_BINARY_DIR}/external/project_name/build

    CONFIGURE_COMMAND <configure_command>

    BUILD_COMMAND <build_command>

    INSTALL_COMMAND <install_command>

# ... 其他选项 )

这种方法允许你控制外部项目的下载、配置、构建和安装过程。

3‌.静态或动态链接库方式‌:
如果另一个项目已经编译成了一个静态库(.a文件)或动态库(.so.dll文件),你可以在你的主项目中链接这个库。你需要在CMake中指定库的路径和要链接的库文件。

# 指定库的路径 link_directories(/path/to/your/library)

# 链接库 target_link_libraries(your_target_name your_library_name)

确保库文件的路径在LD_LIBRARY_PATH环境变量中(对于Linux和macOS),或者在系统的动态链接库搜索路径中(对于Windows)。

4‌.使用Qt的qmake构建系统时的特殊处理‌:
如果你的主项目是使用Qt的qmake构建的,而不是CMake,那么你需要将另一个CMake项目的构建结果(如库文件)集成到qmake项目中。这通常涉及到在qmake的项目文件(.pro文件)中指定库文件的路径和名称。

# 在.pro文件中 LIBS += -L/path/to/your/library -lyour_library_name

对于CMake构建的子项目,你可能需要先单独构建它,然后将生成的库文件和其他必要的文件复制到主项目可以访问的位置。

在Qt和CMake的上下文中,最常见和推荐的方法是使用子目录方式(如果子项目可以很容易地包含在主项目中)或静态/动态链接库方式(如果子项目已经编译成了库)。这些方法提供了较好的集成度和灵活性。如果你选择使用ExternalProject方式,请注意它可能会增加构建的复杂性和时间,因为外部项目会在每次构建主项目时被下载和构建(除非你已经缓存了构建结果)。

要把一个项目编译成一个静态库(.a 文件)或动态库(.so.dll 文件),需要按照以下步骤:

1. 编写源代码

首先,确保项目源代码是组织良好的,并且有一个清晰的构建系统(如 CMake 或 Makefile)。

2. 配置构建系统

使用 CMake

如果使用了 CMake,在 CMakeLists.txt 文件中指定要生成的库类型。以下是一个简单的例子:

project(MyLibrary)# 设置项目名称

set(CMAKE_CXX_STANDARD 11) # 指定 C++ 标准

set(SOURCE_FILES src/file1.cpp src/file2.cpp)# 添加源文件

add_library(MyStaticLib STATIC ${SOURCE_FILES})# 添加一个静态库目标

# 或者添加一个动态库目标

# add_library(MyDynamicLib SHARED ${SOURCE_FILES})

在这个例子中,MyStaticLib 是静态库的目标名称,而 MyDynamicLib 是动态库的目标名称(注释掉了,因为通常只会选择其中一个)。${SOURCE_FILES} 包含了要编译的源文件列表。

使用 Makefile

如果使用 Makefile,需要编写规则来编译源文件并生成库文件。以下是一个简单的 Makefile 片段,用于生成静态库:

# 编译器和编译器标志

CXX = g++ CXXFLAGS = -std=c++11

# 源文件和对象文件

SRCS = src/file1.cpp src/file2.cpp OBJS = $(SRCS:.cpp=.o)

# 库文件名称

TARGET = libMyStaticLib.a

# 编译规则

all: $(TARGET) $(TARGET): $(OBJS) @echo "Creating static library $(TARGET)..." @ar rcs $(TARGET) $(OBJS) %.o: %.cpp @echo "Compiling $<..." @$(CXX) $(CXXFLAGS) -c $< -o $@

# 清理规则 clean: @echo "Cleaning up..." @rm -f $(OBJS) $(TARGET)

对于动态库,你需要将 TARGET 变量改为 libMyDynamicLib.so(Linux)或相应的 .dll 名称(Windows),并调整编译和链接规则以生成动态库。

3. 编译库

使用 CMake

在项目的根目录下运行以下命令:

mkdir build

cd build

cmake ..

make

这将创建一个 build 目录,并在其中生成静态库或动态库文件。

使用 Makefile

在项目的根目录下运行 make 命令:

make

这将根据 Makefile 中的规则编译源文件并生成库文件。

4. 使用库

一旦库文件生成,你可以在其他项目中使用它。对于静态库,你需要在编译时指定库文件的路径和名称,并使用 -L(指定库目录)和 -l(指定库名称,不包括前缀 lib 和文件扩展名)选项。对于动态库,你还需要确保库文件在运行时是可访问的,通常是通过设置 LD_LIBRARY_PATH 环境变量(Linux)或将库文件放在系统的动态链接库搜索路径中(Windows)。

注意事项

  • 确保你的源代码中没有 main 函数,因为库不应该包含入口点。
  • 对于动态库,你可能还需要处理平台特定的细节,比如导出符号(在 Windows 上使用 __declspec(dllexport))和导入符号(在 Windows 上使用 __declspec(dllimport))。
  • 在编写和使用库时,考虑库的 API 设计和文档,以便其他开发者能够轻松地使用你的库。

扩展:

1.动态链接库和静态链接库有什么区别

动态链接库(Dynamic Link Library, DLL)和静态链接库(Static Link Library)在程序编译和运行时的行为上有着显著的区别。以下是它们的主要区别:

  1. 链接时机‌:

    • 动态链接库:在程序运行时被加载和链接。这意味着程序在编译时并不包含这些库的代码,而是在运行时从外部文件中加载。
    • 静态链接库:在程序编译时就被完全集成到程序中。库代码在编译时就被复制到最终的可执行文件中。
  2. 文件大小和内存占用‌:

    • 动态链接库:使用动态链接库的程序通常具有更小的文件大小,因为库代码不包含在可执行文件中。但如果多个程序使用相同的库,这些程序可以共享内存中的同一份库副本,从而减少总体内存占用。
    • 静态链接库:会增加最终可执行文件的大小,因为每一个使用该库的程序都包含了一份完整的库代码副本。这可能导致更高的磁盘空间和内存占用,尤其是在多个程序使用相同库的情况下。
  3. 部署和更新‌:

    • 动态链接库:使得部署和更新变得更加简单。当库需要更新时,只需替换掉系统中的DLL文件,而不需要重新编译使用该库的每个程序。
    • 静态链接库:中的代码更新需要重新编译所有使用该库的程序。
  4. 兼容性和依赖问题‌:

    • 动态链接库:可能导致所谓的“DLL地狱”,即版本冲突和缺失问题,因为不同的程序可能依赖于同一DLL的不同版本。
    • 静态链接库:由于是编译到程序中的,不会有版本冲突的问题,但这也意味着更新库版本需要重新编译程序。
  5. 平台和语言限制‌:

    • 动态链接库:在不同的操作系统平台(如Windows的DLL和Linux的SO文件)和不同的编程语言间可能存在兼容性问题。
    • 静态链接库:通常与特定的编译器和平台紧密相关,可能在跨平台时遇到限制。
  6. 使用场景‌:

    • 动态链接库:更适用于需要频繁更新或者多个程序共享代码的情况。
    • 静态链接库:更适用于小型、独立的应用程序,或者对性能有特别要求的场合。

总的来说,动态链接库和静态链接库各有优劣,选择使用哪一种通常取决于应用程序的特定需求和部署环境。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/950647.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

(2023|NIPS,LLaVA-Med,生物医学 VLM,GPT-4 生成自指导指令跟随数据集,数据对齐,指令调优)

LLaVA-Med: Training a Large Language-and-Vision Assistant for Biomedicine in One Day 目录 LLaVA-Med: Training a Large Language-and-Vision Assistant for Biomedicine in One Day 0. 摘要 1. 简介 2. 相关工作 3. 生物医学视觉指令数据 4. 将多模态对话模型适配…

深入理解Mybatis原理》MyBatis的sqlSessi

sqlSessionFactory 与 SqlSession 正如其名&#xff0c;Sqlsession对应着一次数据库会话。由于数据库会话不是永久的&#xff0c;因此Sqlsession的生命周期也不应该是永久的&#xff0c;相反&#xff0c;在你每次访问数据库时都需要创建它&#xff08;当然并不是说在Sqlsession…

Numpy数组的属性

NumPy中最重要的一个特点就是其n维数组对象&#xff0c;即ndarray(别名array)对象&#xff0c;该对象具有矢量算术能力和复杂的广播能力&#xff0c;可以执行一些科学计算。不同于Python内置的数组类型&#xff0c; array对象拥有对高维数组的处理能力&#xff0c;这也是数值计…

(十)提示词任务分解的策略探讨

&#x1f4e2;&#x1f4e2;&#x1f4e2; 大家好&#xff0c;我是云楼Yunlord&#xff0c;CSDN博客之星人工智能领域前三名&#xff0c;多年人工智能学习工作经验&#xff0c;一位兴趣稀奇古怪的【人工智能领域博主】&#xff01;&#xff01;&#xff01;&#x1f61c;&#…

01 数据分析介绍及工具准备

数据分析介绍及工具准备 一、工具准备二、下载和使用Anaconda三、jupyter notebook常用快捷键 一、工具准备 数据科学库 NumPy&#xff0c;SciPy&#xff0c;Pandas&#xff0c;Scikit-Learn 数据可视化库 Matplotlib&#xff0c;Seaborn 编译器 Jupyter Notebook 数据科…

excel表格二维X、Y坐标散点图

excel中存在两列或两行数据&#xff0c;分别表示x坐标和对应的y坐标&#xff0c;同时选中两列或两行数据&#xff1a; 依次选择菜单&#xff0c;插入&#xff0c;图标&#xff0c;XY散点图 可以看到在表格中生成了以第1列为X轴&#xff0c;第2列为Y轴的二维XY散点图&#xff…

Cursor无限续杯——解决Too many free trials.

前情提要 我们都知道Cursor对新用户是有14天且500条免费限制的。 一般情况下&#xff0c;当14天过期&#xff0c;是可以注销账户再重新注册&#xff0c;这样就可以继续拥有14天的体验时长。 但是&#xff01;&#xff01;如果使用超过500次&#xff0c;Cusor就会把你的电脑I…

HCIE-day10-ISIS

ISIS ISIS&#xff08;Intermediate System-to-Intermediate System&#xff09;中间系统到中间系统&#xff0c;属于IGP&#xff08;内部网关协议&#xff09;&#xff1b;是一种链路状态协议&#xff0c;使用最短路径优先SPF算法进行路由计算&#xff0c;与ospf协议有很多相…

洛谷P1617———数字转英文

题目如下 思路&#xff1a;将1~9的英文和20~90的英文用字符串数组存储&#xff0c;把下标看作对应的数字进行输出&#xff0c;遇到0或连续多个0就输出“and”&#xff0c;定义l用来看枚举到哪一位了&#xff0c;如果是单独输入一个“0”&#xff0c;则直接输出zero然后结束。否…

UnityRenderStreaming使用记录(五)

UnityRenderStreaming不一样的错误&#xff0c;船新的版本 继续docker部署UnityRenderStreamingdockerfile一些命令出现了新的错误先解决一个报错不知道怎么解决&#xff0c;先跑个glxgears测试一下先解决MESA和glx的问题新的log&#xff0c;额新的错误尝试解决libnvidia-encod…

Unity-Mirror网络框架-从入门到精通之AdditiveScenes 示例

文章目录 前言Additive Levels和Additive ScenesAdditive Levels场景介绍Portal传送门FadeInOut特效 Additive Scenes示例介绍ZoneHandlerSceneMassage 最后 前言 在现代游戏开发中&#xff0c;网络功能日益成为提升游戏体验的关键组成部分。Mirror是一个用于Unity的开源网络框…

Mac-docker配置

1.配置的文件路径 cd ~/.docker (base) zhangyaweimacbookair .docker % ls buildx cli-plugins config.json contexts daemon.json desktop-build mutagen run (base) zhangyaweimacbookair .docker % cat daemon.json## 重启docker服务 sudo systemctl daemon-reload sudo…

PHP进阶-在Ubuntu上搭建LAMP环境教程

本文将为您提供一个在Ubuntu服务器上搭建LAMP&#xff08;Linux, Apache, MySQL, PHP&#xff09;环境的完整指南。通过本文&#xff0c;您将学习如何安装和配置Apache、MySQL、PHP&#xff0c;并将您的PHP项目部署到服务器上。本文适用于Ubuntu 20.04及更高版本。 一、系统更新…

Elasticsearch(看这一篇就够了)

目录&#xff1a; Elasticsearch介绍正排索引和倒排索引Elasticsearch安装安装ES服务安装服务安装kibana 索引操作创建索引查询索引库修改索引库删除索引库 Elasticsearch常用操作文档操作新增文档查询文档删除文档根据id批量查询文档查询所有文档修改文档部分字段 域的属性分词…

嵌入式技术之Linux(Ubuntu) 一

一、Linux入门 1.硬件和操作系统以及用户的关系 一个传感器&#xff0c;获得数据后&#xff0c;需要向服务器发送数据。传感器传数据给上位机。 上位机需要一个程序来接收数据&#xff0c;那么这个上位机是什么机器&#xff1f; 我们的笔记本电脑就可以当成上位机。 两个手…

【实用技能】如何使用 .NET C# 中的 Azure Key Vault 中的 PFX 证书对 PDF 文档进行签名

TX Text Control 是一款功能类似于 MS Word 的文字处理控件&#xff0c;包括文档创建、编辑、打印、邮件合并、格式转换、拆分合并、导入导出、批量生成等功能。广泛应用于企业文档管理&#xff0c;网站内容发布&#xff0c;电子病历中病案模板创建、病历书写、修改历史、连续打…

oracle闪回恢复数据:(闪回查询,闪回表,闪回库,回收站恢复)

oracle的闪回查询&#xff0c;可以查询提交在表空间的闪回数据&#xff0c;并可以还原所查询的数据&#xff0c;用于恢复短时间内的delele 或者 update 误操作&#xff0c;非常方便&#xff0c;缺点是只能恢复大概几小时内的数据。 文章目录 概要闪回查询恢复数据的主要方法包括…

开放词汇检测新晋SOTA:地瓜机器人开源DOSOD实时检测算法

在计算机视觉领域&#xff0c;目标检测是一项关键技术&#xff0c;旨在识别图像或视频中感兴趣物体的位置与类别。传统的闭集检测长期占据主导地位&#xff0c;但近年来&#xff0c;开放词汇检测&#xff08;Open-Vocabulary Object Detection-OVOD 或者 Open-Set Object Detec…

【网络协议】静态路由详解

网络中的路由器通过以下两种方式之一发现远程网络&#xff1a; 静态配置路由动态路由协议 在本文&#xff0c;我们将学习关于静态路由的各种概念&#xff0c;例如如何配置静态路由、路由表如何进行决策、路由接口等相关知识。 文章目录 引言直连网络静态路由路由表原则原则1原…

(长期更新)《零基础入门 ArcGIS(ArcScene) 》实验七----城市三维建模与分析(超超超详细!!!)

城市三维建模与分析 三维城市模型已经成为一种非常普遍的地理空间数据资源,成为城市的必需品,对城市能化管理至关重要。语义信息丰富的三维城市模型可以有效实现不同领域数据与IS相信息的高层次集成及互操作,从而在城市规划、环境模拟、应急响应和辅助决策等众多领域公挥作用、…