步骤5:安装和测试

练习1 -安装规则

    通常,仅仅构建可执行文件是不够的,它还应该是可安装的。使用CMake,我们可以使用install()命令指定安装规则。

目标

    安装教程可执行文件和MathFunctions库。

需要编辑的文件

MathFunctions/CMakeLists.txt

CMakeLists.txt

步骤

    在Step5目录中提供了起始代码。在这个练习中,完成TODO 1到TODO 4。
    首先,更新MathFunctions/CMakeLists.txt,将MathFunctions和tutorial_compiler_flags库安装到lib目录中。在同一个文件中,指定将MathFunctions.h安装到include目录所需的安装规则。

    然后,更新顶层的CMakeLists.txt,将教程可执行文件安装到bin目录中。最后,所有头文件都应该安装到include目录中。请记住,TutorialConfig.h位于PROJECT_BINARY_DIR中。

实现操作

    项目的安装规则为:
    对于MathFunctions,我们希望分别将库和头文件安装到libinclude目录中。
    对于教程可执行文件,我们希望分别将可执行文件和配置的头文件安装到bin和include目录中。

    因此,在MathFunctions/CMakeLists.txt的末尾,我们添加:

    第1步:

//定义一个变量installable_libs,其中包含了两个值:MathFunctions和tutorial_compiler_flags。这些通常是指CMake项目中的目标(target)或库(library),用于后续的安装步骤。
set(installable_libs MathFunctions tutorial_compiler_flags)

//判断是否存在名为SqrtLibrary的目标。如果存在(即TARGET SqrtLibrary条件成立),则通过list(APPEND ...)命令将SqrtLibrary添加到installable_libs变量的末尾。这样,如果项目中定义了SqrtLibrary目标,它就会被包含在安装列表中。
if(TARGET SqrtLibrary)
  list(APPEND installable_libs SqrtLibrary)
endif()

//install命令来指定将哪些目标安装到指定的目标路径(DESTINATION lib)。${installable_libs}变量在这里用作install命令的参数,表示安装这些目标或库。根据之前的定义和条件判断,可能包括MathFunctions、tutorial_compiler_flags以及可选的SqrtLibrary(如果存在)。
install(TARGETS ${installable_libs} DESTINATION lib)

   第2步:

install(FILES MathFunctions.h DESTINATION include)

    install 是CMake提供的一个命令,用于安装文件或目标到指定的位置。
    FILES MathFunctions.h 指定了要安装的文件列表,这里只有一个文件 MathFunctions.h。
    DESTINATION include 指定了安装的目标路径。在这里,include 表示将文件安装到目标路径下的 include 子目录中。

这行代码的作用是将项目中的 MathFunctions.h 文件安装到目标路径的 include 目录下,使得其他项目或者用户在使用这个库时可以直接包含这个头文件。

    教程可执行文件和配置的头文件的安装规则是相似的。在顶级CMakeLists.txt的末尾,我们添加:

install(TARGETS Tutorial DESTINATION bin)
install(FILES "${PROJECT_BINARY_DIR}/TutorialConfig.h"
  DESTINATION include
  )

    这就是创建本教程的基本本地安装所需的全部内容。

编译和运行

    新建一个名为Step5_build的目录。从命令行使用cmake命令的--install选项(在3.15中引入,旧版本的cmake必须使用make install)运行安装步骤。这一步将安装适当的头文件、库和可执行文件。例如:

cmake --install .

    对于多配置工具,不要忘记使用--config参数来指定配置。

cmake --install . --config Release

    如果使用IDE,只需构建INSTALL目标。您可以从命令行构建相同的安装目标,如下所示:

cmake --build . --target install --config Debug

    CMake变量CMAKE_INSTALL_PREFIX用于确定文件安装的根目录。如果使用cmake--install命令,可以通过--prefix参数重写安装前缀。例如:

cmake --install . --prefix "/home/myuser/installdir"

    移动到安装目录,并验证安装的教程库是否运行。

练习2 -测试支持

    CTest提供了一种轻松管理项目测试的方法。可以通过add_test()命令添加测试。

目标

    使用CTest为我们的可执行文件创建单元测试。

步骤

    源代码在Step5目录中提供。在这个练习中,完成TODO 5到TODO 9。
    首先,我们需要启用测试。接下来,开始使用add_test()向项目添加测试。我们将添加3个简单的测试。

具体操作

    在顶层CMakeLists.txt文件的末尾,我们首先需要使用enable_testing()命令启用测试。

enable_testing()

    启用测试后,我们将添加一些基本测试来验证应用程序是否正常工作。首先,使用add_test()创建一个测试,它运行教程可执行文件,并传入参数25。此测试将验证应用程序是否运行,没有出现分段故障或以其他方式崩溃,并且返回值为零。

add_test(NAME Runs COMMAND Tutorial 25)
  • add_test 是 CMake 的命令,用于添加一个测试。它会创建一个新的测试,并将其添加到 CTest 的测试套件中。
  • NAME Runs 指定了测试的名称为 "Runs"。这个名称是用来标识测试的唯一标识符,用于在测试结果中查找和报告。
  • COMMAND Tutorial 25 指定了要运行的命令。在这里,"Tutorial" 是要执行的可执行文件的名称,而 "25" 则是传递给该可执行文件的参数。

     这行代码的目的是创建一个名为 "Runs" 的测试,该测试会运行名为 "Tutorial" 的可执行文件,并传递整数参数 25 给这个可执行文件。此测试的主要目标是验证以下几点:

  1. 应用程序能够正常运行,即不会因为段错误或其他崩溃而终止。
  2. 应用程序的返回值应为零,这表示程序在运行过程中没有遇到严重错误或异常情况。

    这种测试方法适用于验证应用程序的基本运行情况,而不涉及具体的计算结果是否正确,主要关注程序是否能够在最基本的情况下正常启动和结束。

    接下来,让我们使用PASS_REGULAR_EXPRESSION测试属性来验证测试的输出是否包含某些字符串。在本例中,验证当提供的参数数量不正确时是否打印usage消息。

add_test(NAME Usage COMMAND Tutorial)
set_tests_properties(Usage
  PROPERTIES PASS_REGULAR_EXPRESSION "Usage:.*number"
  )
  1. add_test(NAME Usage COMMAND Tutorial)

    • add_test 命令创建一个名为 "Usage" 的测试。
    • NAME Usage 指定了测试的名称为 "Usage"。这个名称用于在测试结果中标识和查找测试。
    • COMMAND Tutorial 指定了要运行的命令或可执行文件为 "Tutorial"。这表示测试会执行名为 "Tutorial" 的可执行文件。
  2. set_tests_properties(Usage PROPERTIES PASS_REGULAR_EXPRESSION "Usage:.*number")

    • set_tests_properties 是 CMake 的命令,用于设置测试的属性。
    • Usage 是之前定义的测试名称,这里是 "Usage"。
    • PROPERTIES 关键字用于指定要设置的属性。
    • PASS_REGULAR_EXPRESSION 是一个测试属性,它指定了一个正则表达式模式。
    • "Usage:.*number" 是一个正则表达式,它描述了期望在测试的输出中匹配的字符串模式。具体含义是:
      • Usage::输出中应包含 "Usage:" 这个字符串。
      • .*:表示任意数量的任意字符,这里是用来匹配 "Usage:" 后面可能存在的其他字符。
      • number:输出中还应包含 "number" 这个单词。

    这段代码的作用是创建一个名为 "Usage" 的测试,测试会运行名为 "Tutorial" 的可执行文件,并且验证该可执行文件的输出中是否包含 "Usage:" 和 "number"。如果测试输出符合这个正则表达式模式,那么测试将被视为通过;否则,测试将失败。这种方法可以用来验证程序在特定情况下是否输出了预期的使用说明或错误信息。

    接下来将添加的下测试命令来验证计算值为平方根,如下所示:

add_test(NAME StandardUse COMMAND Tutorial 4)
set_tests_properties(StandardUse
  PROPERTIES PASS_REGULAR_EXPRESSION "4 is 2"
  )
  1. add_test(NAME StandardUse COMMAND Tutorial 4)

    • add_test 命令创建一个名为 "StandardUse" 的测试。
    • NAME StandardUse 指定了测试的名称为 "StandardUse"。
    • COMMAND Tutorial 4 指定了要运行的命令为 "Tutorial",并传递整数参数 4 给这个可执行文件。这表示测试会执行名为 "Tutorial" 的可执行文件,并向其传递参数 4。
  2. set_tests_properties(StandardUse PROPERTIES PASS_REGULAR_EXPRESSION "4 is 2")

    • set_tests_properties 命令用于设置测试的属性。
    • StandardUse 是之前定义的测试名称。
    • PROPERTIES 关键字用于指定要设置的属性。
    • PASS_REGULAR_EXPRESSION 是一个测试属性,指定了一个正则表达式模式。
    • "4 is 2" 是正则表达式,描述了测试输出中预期要匹配的字符串。

    这段代码的目的是创建一个名为 "StandardUse" 的测试,该测试会运行名为 "Tutorial" 的可执行文件,传递参数 4 给它。然后,它验证该可执行文件的输出中是否包含字符串 "4 is 2"。这样的验证通常用于确保程序在计算平方根时,输出确实是预期的平方根值。例如,这里期望的输出是 "4 is 2",表示对于输入 4,程序应输出其平方根值为 2。如果输出符合这个正则表达式模式,测试将被视为通过;否则,测试将失败。

    这一个测试还不足以让我们确信它对传入的所有值都有效。我们应该增加更多的测试来验证这一点。为了方便地添加更多测试,我们创建了一个名为do_test的函数,该函数运行应用程序并验证给定输入的计算平方根是否正确。

function(do_test target arg result)
  add_test(NAME Comp${arg} COMMAND ${target} ${arg})
  set_tests_properties(Comp${arg}
    PROPERTIES PASS_REGULAR_EXPRESSION ${result}
    )
endfunction()

# do a bunch of result based tests
do_test(Tutorial 4 "4 is 2")
do_test(Tutorial 9 "9 is 3")
do_test(Tutorial 5 "5 is 2.236")
do_test(Tutorial 7 "7 is 2.645")
do_test(Tutorial 25 "25 is 5")
do_test(Tutorial -25 "-25 is (-nan|nan|0)")
do_test(Tutorial 0.0001 "0.0001 is 0.01")

1.函数定义 do_test

function(do_test target arg result)
  add_test(NAME Comp${arg} COMMAND ${target} ${arg})
  set_tests_properties(Comp${arg}
    PROPERTIES PASS_REGULAR_EXPRESSION ${result}
  )
endfunction()
  • function(do_test target arg result):定义了一个名为 do_test 的函数,它接受三个参数:

    • target:表示要运行的可执行文件的名称。
    • arg:表示传递给可执行文件的参数。
    • result:是一个正则表达式,用于验证测试的输出是否符合预期。
  • add_test(NAME Comp${arg} COMMAND ${target} ${arg}):在这个函数中,首先使用 add_test 命令创建一个新的测试。

    • NAME Comp${arg}:指定了测试的名称,这里会根据传入的参数 arg 动态生成,确保每个测试名称是唯一的。
    • COMMAND ${target} ${arg}:指定要运行的命令和参数,即运行 ${target} 可执行文件,并传递 ${arg} 作为参数。
  • set_tests_properties(Comp${arg} PROPERTIES PASS_REGULAR_EXPRESSION ${result}):接着,使用 set_tests_properties 命令设置测试的属性。

    • Comp${arg}:指定要设置属性的测试名称。
    • PROPERTIES PASS_REGULAR_EXPRESSION ${result}:将 PASS_REGULAR_EXPRESSION 属性设置为 ${result},这个属性告诉测试框架应该用正则表达式 ${result} 来匹配测试输出,以验证测试是否通过。

2.调用 do_test 函数

  1. # do a bunch of result based tests
    do_test(Tutorial 4 "4 is 2")
    do_test(Tutorial 9 "9 is 3")
    do_test(Tutorial 5 "5 is 2.236")
    do_test(Tutorial 7 "7 is 2.645")
    do_test(Tutorial 25 "25 is 5")
    do_test(Tutorial -25 "-25 is (-nan|nan|0)")
    do_test(Tutorial 0.0001 "0.0001 is 0.01")
    
    • 这部分代码展示了如何使用 do_test 函数来添加多个测试。
    • 每个 do_test 调用都会添加一个新的测试,指定了要运行的可执行文件 Tutorial,传递给它的参数以及预期的输出结果。
    • 例如,do_test(Tutorial 4 "4 is 2") 表示添加一个测试,运行 Tutorial 可执行文件,传递参数 4,并期望输出包含字符串 "4 is 2"。

    通过这种方式,使用 do_test 函数可以大大简化添加测试的过程,并确保每个测试都验证了平方根计算的正确性,从而增加了代码的可靠性和测试覆盖率。

编译和运行

    移动到编译目录并重新编译程序。然后,运行ctest执行命令:ctest -N或ctest -VV。对于多配置生成器(例如Visual Studio),必须使用-C <mode>标志指定配置类型。例如,要在Debug模式下运行测试,执行ctest -C Debug -VV。

  1. ctest -N

    • -N 选项用于进行测试的预览,也称为显示测试。它不会真正运行测试,而是列出将要运行的测试列表。
    • 用法示例:在终端中进入构建目录,然后运行 ctest -N。这将显示将要运行的测试的列表,但不会实际执行测试代码。
  2. ctest -VV

    • -VV 选项用于详细输出,也称为详细输出模式。它会显示更多关于测试的详细信息,包括每个测试用例的输出和其他相关信息。
    • 用法示例:在终端中进入构建目录,然后运行 ctest -VV。这将以详细模式运行测试,并显示详细的输出信息,帮助诊断测试失败或其他问题。
  3. ctest -C Debug -VV

    • -C <mode> 选项用于指定配置模式,例如 Debug 或 Release。对于多配置生成器(如 Visual Studio),这是必需的。
    • -VV 选项用于详细输出模式,详细描述见上述。
    • 用法示例:在终端中进入构建目录,然后运行 ctest -C Debug -VV。这将以 Debug 模式运行测试,并显示详细的输出信息。

总结:

  • ctest -N:显示将要运行的测试列表,但不运行实际的测试代码。
  • ctest -VV:以详细输出模式运行测试,显示更多的测试执行信息。
  • ctest -C Debug -VV:以 Debug 配置模式运行测试,并显示详细的输出信息。

    这些命令可以帮助开发人员管理和执行项目中的测试,提高代码质量和可靠性。

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

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

相关文章

pyrender 离线渲染包安装教程

pyrender 离线渲染包安装教程 安装 安装 官方安装教程:https://pyrender.readthedocs.io/en/latest/install/index.html#installmesa 首先 pip install pyrenderclang6.0安装 下载地址:https://releases.llvm.org/download.html#6.0.0 注意下好是叫&#xff1a;clangllvm-6…

L04_MySQL知识图谱

这些知识点你都掌握了吗&#xff1f;大家可以对着问题看下自己掌握程度如何&#xff1f;对于没掌握的知识点&#xff0c;大家自行网上搜索&#xff0c;都会有对应答案&#xff0c;本文不做知识点详细说明&#xff0c;只做简要文字或图示引导。 1 基础 1.1内部组件结构 1.2 数据…

尚品汇-(十四)

&#xff08;1&#xff09;提交git 商品后台管理到此已经完成&#xff0c;我们可以把项目提交到公共的环境&#xff0c;原来使用svn&#xff0c;现在使用git 首先在本地创建ssh key&#xff1b; 命令&#xff1a;ssh-keygen -t rsa -C "your_emailyouremail.com" I…

用kimi实现一键实体识别与关系抽取

实体识别与关系抽取是自然语言处理&#xff08;NLP&#xff09;中的两个重要任务&#xff0c;通常被视为知识图谱构建的基础技术。 实体识别&#xff08;Named Entity Recognition, NER&#xff09;&#xff1a; 实体识别的目标是从文本中识别出具有特定意义的实体&#xff0…

动手学深度学习(Pytorch版)代码实践 -循环神经网络- 56门控循环单元(`GRU`)

56门控循环单元&#xff08;GRU&#xff09; 我们讨论了如何在循环神经网络中计算梯度&#xff0c; 以及矩阵连续乘积可以导致梯度消失或梯度爆炸的问题。 下面我们简单思考一下这种梯度异常在实践中的意义&#xff1a; 我们可能会遇到这样的情况&#xff1a;早期观测值对预测…

Nacos2.X源码分析:服务注册、服务发现流程

文章目录 Nacos2.1.X源码源码下载服务注册NacosClient端NacosServer端 服务发现NacosClient端NacosServer端 Nacos2.1.X源码 源码下载 源码下载地址 服务注册 官方文档&#xff0c;对于NamingService接口服务注册方法的说明 Nacos2.X 服务注册总流程图 NacosClient端 一个…

华为OSPF配置DR和BDR与指定DR

基础配置 <Huawei>sys #进入配置模式 Enter system view, return user view with CtrlZ. [Huawei]un in en #关闭报文弹窗 Info: Information center is disabled. [Huawei]sys R1 #设备名更改为R1 [R1]int g0/0/0 …

智能物联网鱼缸

硬件部分及接线图 工具 继电器、开发板、物联网os、云平台 微信小程序 结构&#xff1a;images、pages两个为主体。 标题头部分 <view class"container"> <view class"head_box"> <image src"/images/面性鱼缸.png"><…

【Java】详解String类中的各种方法

创建字符串 常见的创建字符串的三种方式&#xff1a; // 方式一 String str "hello world"; // 方式二 String str2 new String("hello world"); // 方式三 char[] array {a, b, c}; String str3 new String(array); "hello" 这样的字符串字…

昇思学习打卡-8-FCN图像语义分割

目录 FCN介绍FCN所用的技术训练数据的可视化模型训练模型推理FCN的优点和不足优点不足 FCN介绍 FCN主要用于图像分割领域&#xff0c;是一种端到端的分割方法&#xff0c;是深度学习应用在图像语义分割的开山之作。通过进行像素级的预测直接得出与原图大小相等的label map。因…

3-4 优化器和学习率

3-4 优化器和学习率 主目录点这里 优化器是机器学习和深度学习模型训练过程中用于调整模型参数的方法。它的主要目标是通过最小化损失函数来找到模型参数的最优值&#xff0c;从而提升模型的性能。 在深度学习中&#xff0c;优化器使用反向传播算法计算损失函数相对于模型参数…

C++ 函数高级——函数的占位参数

C中函数的形参列表里可以有占位参数&#xff0c;用来做占位&#xff0c;调用函数时必须填补改位置 语法&#xff1a; 返回值类型 函数名&#xff08;数据类型&#xff09;{ } 在现阶段函数的占位参数存在意义不大&#xff0c;但是后面的课程中会用到该技术 示例&#xff1a;…

TypeScript:5分钟上手创建一个简单的Web应用

一、练习TypeScript实例 1.1 在src目录里创建greeter.ts greeter.ts文件代码 // https://www.tslang.cn/docs/handbook/typescript-in-5-minutes.html // 格式化快捷键&#xff1a;https://blog.csdn.net/Dontla/article/details/130255699 function greeter(name: string) …

Windows电脑下载、安装VS Code的方法

本文介绍Visual Studio Code&#xff08;VS Code&#xff09;软件在Windows操作系统电脑中的下载、安装、运行方法。 Visual Studio Code&#xff08;简称VS Code&#xff09;是一款由微软开发的免费、开源的源代码编辑器&#xff0c;支持跨平台使用&#xff0c;可在Windows、m…

采煤机作业3D虚拟仿真教学线上展示增强应急培训效果

在化工行业的生产现场&#xff0c;安全永远是首要之务。为了加强从业人员的应急响应能力和危机管理能力&#xff0c;纷纷引入化工行业工艺VR模拟培训&#xff0c;让应急演练更加生动、高效。 化工行业工艺VR模拟培训软件基于真实的厂区环境&#xff0c;精确还原了各类事件场景和…

vue2 webpack使用optimization.splitChunks分包,实现按需引入,进行首屏加载优化

optimization.splitChunks的具体功能和配置信息可以去网上自行查阅。 这边简单讲一下他的使用场景、作用、如何使用&#xff1a; 1、没用使用splitChunks进行分包之前&#xff0c;所有模块都揉在一个文件里&#xff0c;那么当这个文件足够大、网速又一般的时候&#xff0c;首…

Transformer-LSTM预测 | Matlab实现Transformer-LSTM多变量时间序列预测

Transformer-LSTM预测 | Matlab实现Transformer-LSTM多变量时间序列预测 目录 Transformer-LSTM预测 | Matlab实现Transformer-LSTM多变量时间序列预测效果一览基本介绍程序设计参考资料 效果一览 基本介绍 1.Matlab实现Transformer-LSTM多变量时间序列预测&#xff0c;Transf…

玫瑰千层烤饼:味蕾的芬芳盛宴

在美食的缤纷世界里&#xff0c;有一种独特的存在&#xff0c;它融合了玫瑰的芬芳与烤饼的酥脆&#xff0c;那便是令人陶醉的甘肃美食玫瑰千层烤饼。食家巷玫瑰千层烤饼&#xff0c;宛如一件精心雕琢的艺术品。每一层薄如纸张的面皮&#xff0c;都承载着制作者的细腻与用心。层…

MySQL Binlog详解:提升数据库可靠性的核心技术

文章目录 1. 引言1.1 什么是MySQL Bin Log&#xff1f;1.2 Bin Log的作用和应用场景 2. Bin Log的基本概念2.1 Bin Log的工作原理2.2 Bin Log的三种格式 3. 配置与管理Bin Log3.1 启用Bin Log3.2 配置Bin Log参数3.3 管理Bin Log文件3.4 查看Bin Log内容3.5 使用mysqlbinlog工具…

vue3项目 前端blocked:mixed-content问题解决方案

一、问题分析 blocked:mixed-content其实浏览器不允许在https页面里嵌入http的请求&#xff0c;现在高版本的浏览器为了用户体验&#xff0c;都不会弹窗报错&#xff0c;只会在控制台上打印一条错误信息。一般出现这个问题就是在https协议里嵌入了http请求&#xff0c;解决方法…