先附一篇参考链接
然后给cmake的官网帮助地址:https://cmake.org/cmake/help/v3.10/index.html
可以在上面找到所有的cmake命令的解释,cmake命令共分成4类
- Scripting Commands 脚本命令
- 项目命令
- CTest Commands
- Deprecated Commands 不推荐使用的命令
说一下QT建立工程的过程
后面在编译选项的时候要选择cmake,它一开始默认是qmake,如果使用的是qmake,那么工程生成的是.pro的配置文件,所以这里要选择cmake,会生成cmakelist.txt的配置文件
cmake_minimum_required(VERSION 2.8)
project(test)
add_executable(${PROJECT_NAME} "main.cpp")
set(CMAKE_CXX_STANDARD 11)
find_package(OpenCV 4.4.0 REQUIRED)
target_link_libraries(test ${OpenCV_LIBS})
解释:
在项目新建完成之后,第1-3行是默认生成的。
1:版本要求指定 cmake 的最小版本
2:工程名设置项目名称
3:把项目名和执行主函数 放一块 执行//相当于生成可执行文件
这3个是cmake的最低配置要求
4:配置设置设置变量
set共有3个作用
1.普通变量
set(<variable> <value>... [PARENT_SCOPE])
设置变量<variable> 的值为 <value>
如果后面增加了 PARENT_SCOPE 选项的话, 表示 在上层作用域/目录 设置<variable> 的值为 <value>, 但是当前作用域/目录 该<variable> 的值不变。
2. 设置缓存条目
set(<variable> <value>... CACHE <type> <docstring> [FORCE])
设置给定的缓存变量<variable> 的值为 <value>.
由于缓存项旨在提供用户可设置的值,因此默认情况下不会覆盖现有缓存项。使用FORCE选项覆盖现有条目。
3.设置环境变量
set(ENV{<variable>} [<value>])
设置环境变量<variable>的值为<value>. 后面使用 $ENV{<variable>}
可以获取该值.
5:额外需要库
find_packag()是一个搜包命令,能够将第三方的开源库一整个直接导入进来。
根据cmake官方文档可以知道,find_package()
有Module模式(基本用法,basic signature)和Config模式(full signature,完全用法),其中Module模式是基础,Config模式则更复杂高级些。
区分Module模式和Config模式
Module模式也就是基础用法(Basic Signature,这里Signature表示“用法”,而不是“签名”),Config模式也就是高级用法(Full Signature)
也就是说,只有这3种情况下才是Config模式:
-
find_package()
中指定CONFIG
关键字 -
find_package()
中指定NO_MODULE
关键字 -
find_package()
中使用了不在"basic signature"(也就是Module模式下所有支持的配置)关键字
Module模式下find_package()
的用法
find_package(<package> [version] [EXACT] [QUIET] [MODULE]
[REQUIRED] [[COMPONENTS] [components...]]
[OPTIONAL_COMPONENTS components...]
[NO_POLICY_SCOPE])
version
和EXACT
: 都是可选的,version
指定的是版本,如果指定就必须检查找到的包的版本是否和version
兼容。如果指定EXACT
则表示必须完全匹配的版本而不是兼容版本就可以。
QUIET
可选字段,表示如果查找失败,不会在屏幕进行输出(但是如果指定了REQUIRED
字段,则QUIET
无效,仍然会输出查找失败提示语)。
MODULE
可选字段。前面提到说“如果Module模式查找失败则回退到Config模式进行查找”,但是假如设定了MODULE
选项,那么就只在Module模式查找,如果Module模式下查找失败并不回落到Config模式查找。
REQUIRED
可选字段。表示一定要找到包,找不到的话就立即停掉整个cmake。而如果不指定REQUIRED
则cmake会继续执行。
COMPONENTS
,components
:可选字段,表示查找的包中必须要找到的组件(components),如果有任何一个找不到就算失败,类似于REQUIRED
,导致cmake停止执行。
OPTIONAL_COMPONENTS
和components
:可选的模块,找不到也不会让cmake停止执行。
Module模式查找顺序
Module模式下是要查找到名为Find<PackageName>.cmake
的文件。
先在CMAKE_MODULE_PATH
变量对应的路径中查找。如果路径为空,或者路径中查找失败,则在cmake module directory(cmake安装时的Modules目录,比如/usr/local/share/cmake/Modules
)查找。
后面还有configure模式下的用法,参考链接:https://www.jianshu.com/p/39fc5e548310
6:链接 所需要的库(工程名和库名) 特别容易出错
add_library(common STATIC util.cpp) # 生成静态库
add_library(common SHARED util.cpp) # 生成动态库或共享库
add_library 默认生成是静态库,通过以上命令生成文件名字,
- 在 Linux 下是:
demo
libcommon.a
libcommon.so - 在 Windows 下是:
demo.exe
common.lib
common.dll
1.add_library该指令的主要作用就是将指定的源文件生成链接文件,然后添加到工程中去
//Normal Libraries
add_library(<name> [STATIC | SHARED | MODULE]
[EXCLUDE_FROM_ALL]
source1 [source2 ...])
//Imported Libraries
add_library(<name> <SHARED|STATIC|MODULE|OBJECT|UNKNOWN> IMPORTED
[GLOBAL])
//Object Libraries
add_library(<name> OBJECT <src>...)
//Alias Libraries
add_library(<name> ALIAS <target>)
//Interface Libraries
add_library(<name> INTERFACE [IMPORTED [GLOBAL]])
其中<name>表示库文件的名字,该库文件会根据命令里列出的源文件来创建。而STATIC、SHARED和MODULE的作用是指定生成的库文件的类型。STATIC库是目标文件的归档文件,在链接其它目标的时候使用。SHARED库会被动态链接(动态链接库),在运行时会被加载。MODULE库是一种不会被链接到其它目标中的插件,但是可能会在运行时使用dlopen-系列的函数。默认状态下,库文件将会在于源文件目录树的构建目录树的位置被创建,该命令也会在这里被调用。
而语法中的source1 source2分别表示各个源文件。
2.link_directories 设置链接库搜索目录
link_directories(directory1 directory2 ...)
该指令的作用主要是指定要链接的库文件的路径,该指令有时候不一定需要。因为find_package和find_library指令可以得到库文件的绝对路径。不过你自己写的动态库文件放在自己新建的目录下时,可以用该指令指定该目录的路径以便工程能够找到。
3.target_link_libraries 设置 target 需要链接的库
该指令的作用为将目标文件与库文件进行链接。
target_link_libraries(<target> [item1] [item2] [...]
[[debug|optimized|general] <item>] ...)
上述指令中的<target>是指通过add_executable()和add_library()指令生成已经创建的目标文件。而[item]表示库文件没有后缀的名字。默认情况下,库依赖项是传递的。当这个目标链接到另一个目标时,链接到这个目标的库也会出现在另一个目标的连接线上。这个传递的接口存储在interface_link_libraries的目标属性中,可以通过设置该属性直接重写传递接口。
至此,完成整个工程项目的配置,如果有报错的情况,请根据错误信息百度解决
最后给一个参考链接,也是对于cmake语法的介绍,这个比较完整,我上面所述的是针对本次工程配置所需的语法使用介绍