CMake中include指令介绍

本文主要介绍CMake中include指令的相关知识。

1 概述

引用CMake官网中对于include指令的介绍,如下:

Load and run CMake code from a file or module.

include指令的用法如下:

include(<file|module> [OPTIONAL] [RESULT_VARIABLE <VAR>] [NO_POLICY_SCOPE])

详细描述如下:

Load and run CMake code from the file given. Variable reads and writes access the scope of the caller(dynamic scoping). If OPTIONAL is present, then no error is raised if the file does not exist. If RESULT_VARIABLE is given, the variable will be set to the full filename which has been included or NOTFOUND if it failed.

If a module is specified instead of a file, the file with name <modulename>.cmake is searched first in CMAKE_MODULE_PATH, then in the CMake module directory. There is one exception to this: if the file which calls include() is located itself in the CMake builtin module directory, then first the CMake builtin module directory is searched and CMAKE_MODULE_PATH afterwards. See also policy CMP0017.

See the cmake_policy() command documentation for discussion of the NO_POLICY_SCOPE option.

2 作用

从上述内容可知,include指令用来载入并运行来自于文件或模块的CMake代码。

在这里针对一些具体的问题场景,介绍include指令的具体用法。

2.1 多C++标准版本指定

有时遇到这样一种需求,在使用同一个外层CMakeLists.txt的前提下,每个源码子目录中要求使用的C++标准版本不同,有的源码要求使用C++98标准编译、有的源码要求使用C++11标准编译,这时就可以使用include指令来满足该需求。

2.1.1 项目代码结构及内容

此处使用《CMake用法示例》博文中的项目代码结构,并在其基础上做一些改动,改动后的项目代码结构如下:

相比于改动前的项目代码结构,这里新增了“cmake_dir3”源码目录,同时,修改了最外层的CMakeLists.txt。

cmake_dir3目录中包含的文件列表如下:

[root@node1 /opt/liitdar/mydemos/simples/cmake_test]# l cmake_dir3
total 8
-rw-r--r--. 1 root root 257 Jul 21 14:19 CMakeLists.txt
-rw-r--r--. 1 root root 258 Jul 21 14:19 main.cpp
[root@node1 /opt/liitdar/mydemos/simples/cmake_test]# 

cmake_dir3文件夹中的CMakeLists.txt内容如下:

# 遍历当前路径下的所有源文件,并将其添加到变量DIR_SRCS中
aux_source_directory(. DIR_SRCS)

# 添加名为cmake_test3的可执行文件,该文件会由变量DIR_SRCS中的源文件构建生成
add_executable(cmake_test3 ${DIR_SRCS})

源码文件main.cpp内容如下:

#include <iostream>
#include <string>

using namespace std;

int main()
{
    int a = 100;
    string strTest;

    strTest = to_string(a) + " is a string.";

    cout << "a is: " << a << endl;
    cout << "pszTest is: " << strTest << endl;

    return 0;
}

最外层的CMakeLists.txt改动部分(新增了cmake_dir3源码目录)如下:

2.1.2 项目构建

对上述项目使用CMake进行构建,过程信息如下:

通过上图可知,项目构建失败了,因为在cmake_dir3文件夹下的main.cpp文件中存在“to_string”函数,该函数需要在C++11标准下进行编译,而项目默认使用的是C++98标准。

2.1.3 解决方案

此时,就需要为cmake_dir3设置不同的C++标准进行编译了。具体步骤如下:

1. 在最外层的CMakeList.txt的同级目录下,增加一个“set_cxx_norm.cmake”文件,如下:

文件set_cxx_norm.cmake的内容如下:

# set c++ norm value, these values will be used for comparision later
set(CXX_NORM_CXX98 1)   # C++98
set(CXX_NORM_CXX03 2)   # C++03
set(CXX_NORM_CXX11 3)   # C++11

# Set the wanted C++ norm
# Adds the good argument to the command line in function of the compiler
macro(set_cxx_norm NORM)
    # Extract c++ compiler --version output
    exec_program(
        ${CMAKE_CXX_COMPILER}
        ARGS --version
        OUTPUT_VARIABLE _compiler_output
    )
    # Keep only the first line
    string(REGEX REPLACE
        "(\n.*$)"
        ""
        cxx_compiler_version "${_compiler_output}"
    )
    # Extract the version number
    string(REGEX REPLACE
        "([^0-9.])|([0-9.][^0-9.])"
        ""
        cxx_compiler_version "${cxx_compiler_version}"
    )

    # Set the specific C++ norm According 'NORM'
    if(${NORM} EQUAL ${CXX_NORM_CXX98})
        add_definitions("-std=c++98")
    elseif(${NORM} EQUAL ${CXX_NORM_CXX03})
        add_definitions("-std=c++03")
    elseif(${NORM} EQUAL ${CXX_NORM_CXX11})
        if(${cxx_compiler_version} VERSION_LESS "4.7.0")
            add_definitions("-std=c++0x")
        else()
            add_definitions("-std=c++11")
        endif()
    endif()

endmacro()

2. 然后,通过修改最外层的CMakeLists.txt,使用include指令引入set_cxx_norm.cmake文件,这样就可以在源码目录中设置想要使用的C++标准了。CMakeList.txt中新增的include指令如下:

3. 最后,修改cmake_dir3的CMakeLists.txt文件,新增“要使用C++11标准”的语句,如下:

# 使用C++11标准
set_cxx_norm(${CXX_NORM_CXX11})

完成上述修改后,再次进行项目构建,结果如下:

通过上图可知,项目构建成功了。此时,cmake_test1和cmake_test2使用的是C++98(默认)标准,而cmake_test3使用的是C++11标准。

运行cmake_test3程序,运行结果如下:

上面的运行结果表明,cmake_test3成功调用了C++11标准的“to_string”函数,将整型转换为字符串类型了。

评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

liitdar

赠人玫瑰,手有余香,君与吾共勉

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值