6、CMake基礎:流程控制

流程控制

  • 1. 條件判斷
    • 1.1 基本表達式
    • 1.2 邏輯判斷
    • 1.3 比較
      • 基于數值的比較
      • 基于字符串的比較
    • 1.4 文件操作
    • 1.5 其他
  • 2. 循環
    • 2.1 foreach
      • 方法1
      • 方法2
      • 方法3
      • 方法4
    • 2.2 while

在 CMake 的 CMakeLists.txt 中也可以進行流程控制,也就是說可以像寫 shell 腳本那樣進行條件判斷和循環。

1. 條件判斷

關于條件判斷其語法格式如下:

if(<condition>)<commands>
elseif(<condition>) # 可選快, 可以重復<commands>
else()              # 可選快<commands>
endif()

在進行條件判斷的時候,如果有多個條件,那么可以寫多個elseif,最后一個條件可以使用else,但是開始和結束是必須要成對出現的,分別為:if和endif。

1.1 基本表達式

if(<expression>)

如果是基本表達式,expression 有以下三種情況:常量、變量、字符串。

  1. 如果是1, ON, YES, TRUE, Y, 非零值,非空字符串時,條件判斷返回True
  2. 如果是 0, OFF, NO, FALSE, N, IGNORE, NOTFOUND,空字符串時,條件判斷返回False

1.2 邏輯判斷

if(NOT <condition>)
if(<cond1> AND <cond2>)
if(<cond1> OR <cond2>)
  1. NOT:其實這就是一個取反操作,如果條件condition為True將返回False,如果條件condition為False將返回True。
  2. AND:如果cond1和cond2同時為True,返回True否則返回False。
  3. or:如果cond1和cond2兩個條件中至少有一個為True,返回True,如果兩個條件都為False則返回False。

1.3 比較

基于數值的比較

if(<variable|string> LESS <variable|string>)
if(<variable|string> GREATER <variable|string>)
if(<variable|string> EQUAL <variable|string>)
if(<variable|string> LESS_EQUAL <variable|string>)
if(<variable|string> GREATER_EQUAL <variable|string>)
  1. LESS:如果左側數值小于右側,返回True
  2. GREATER:如果左側數值大于右側,返回True
  3. EQUAL:如果左側數值等于右側,返回True
  4. LESS_EQUAL:如果左側數值小于等于右側,返回True
  5. GREATER_EQUAL:如果左側數值大于等于右側,返回True

基于字符串的比較

if(<variable|string> STRLESS <variable|string>)
if(<variable|string> STRGREATER <variable|string>)
if(<variable|string> STREQUAL <variable|string>)
if(<variable|string> STRLESS_EQUAL <variable|string>)
if(<variable|string> STRGREATER_EQUAL <variable|string>)
  1. STRLESS:如果左側字符串小于右側,返回True
  2. STRGREATER:如果左側字符串大于右側,返回True
  3. STREQUAL:如果左側字符串等于右側,返回True
  4. STRLESS_EQUAL:如果左側字符串小于等于右側,返回True
  5. STRGREATER_EQUAL:如果左側字符串大于等于右側,返回True

1.4 文件操作

if(EXISTS path-to-file-or-directory)

判斷文件或者目錄是否存在:如果文件或者目錄存在返回True,否則返回False。

if(IS_DIRECTORY path)

判斷是不是目錄:此處目錄的 path 必須是絕對路徑。如果目錄存在返回True,目錄不存在返回False。

if(IS_SYMLINK file-name)

此處的 file-name 對應的路徑必須是絕對路徑。如果軟鏈接存在返回True,軟鏈接不存在返回False。
軟鏈接相當于 Windows 里的快捷方式

if(IS_ABSOLUTE path)

關于絕對路徑:如果是Linux,該路徑需要從根目錄開始描述;如果是Windows,該路徑需要從盤符開始描述。
如果是絕對路徑返回True,如果不是絕對路徑返回False。

1.5 其他

if(<variable|string> IN_LIST <variable>)

判斷某個元素是否在列表中。如果這個元素在列表中返回True,否則返回False。

if(<variable|string> PATH_EQUAL <variable|string>)

比較兩個路徑是否相等。關于路徑的比較其實就是兩個字符串的比較,如果路徑格式書寫沒有問題也可以通過下面這種方式進行比較:

if(<variable|string> STREQUAL <variable|string>)

我們在書寫某個路徑的時候,可能由于誤操作會多寫幾個分隔符,比如把/a/b/c寫成/a//b///c,此時通過STREQUAL對這兩個字符串進行比較肯定是不相等的,但是通過PATH_EQUAL去比較兩個路徑,得到的結果確實相等的。
在進行路徑比較的時候,如果使用 PATH_EQUAL 可以自動剔除路徑中多余的分割線然后再進行路徑的對比,使用 STREQUAL 則只能進行字符串比較。

2. 循環

在 CMake 中循環有兩種方式,分別是:foreach和while。

2.1 foreach

使用 foreach 進行循環,語法格式如下:

foreach(<loop_var> <items>)<commands>
endforeach()

通過foreach我們就可以對items中的數據進行遍歷,然后通過loop_var將遍歷到的當前的值取出,在取值的時候有以下幾種用法。

方法1

foreach(<loop_var> RANGE <stop>)
  1. RANGE:關鍵字,表示要遍歷范圍
  2. stop:這是一個正整數,表示范圍的結束值,在遍歷的時候從 0 開始,最大值為 stop。
  3. loop_var:存儲每次循環取出的值
cmake_minimum_required(VERSION 3.2)
project(test)
# 循環
foreach(item RANGE 10)message(STATUS "當前遍歷的值為: ${item}" )
endforeach()

結果:在對一個整數區間進行遍歷的時候,得到的范圍是這樣的 【0,stop】,右側是閉區間包含 stop 這個值。

$ cmake ..
-- 當前遍歷的值為: 0
-- 當前遍歷的值為: 1
-- 當前遍歷的值為: 2
-- 當前遍歷的值為: 3
-- 當前遍歷的值為: 4
-- 當前遍歷的值為: 5
-- 當前遍歷的值為: 6
-- 當前遍歷的值為: 7
-- 當前遍歷的值為: 8
-- 當前遍歷的值為: 9
-- 當前遍歷的值為: 10
-- Configuring done
-- Generating done
-- Build files have been written to: /home/robin/abc/a/build

方法2

foreach(<loop_var> RANGE <start> <stop> [<step>])
  1. RANGE:關鍵字,表示要遍歷范圍
  2. start:這是一個正整數,表示范圍的起始值,也就是說最小值為 start
  3. stop:這是一個正整數,表示范圍的結束值,也就是說最大值為 stop
  4. step:控制每次遍歷的時候以怎樣的步長增長,默認為1,可以不設置
  5. loop_var:存儲每次循環取出的值
cmake_minimum_required(VERSION 3.2)
project(test)foreach(item RANGE 10 30 2)message(STATUS "當前遍歷的值為: ${item}" )
endforeach()

結果:

$ cmake ..
-- 當前遍歷的值為: 10
-- 當前遍歷的值為: 12
-- 當前遍歷的值為: 14
-- 當前遍歷的值為: 16
-- 當前遍歷的值為: 18
-- 當前遍歷的值為: 20
-- 當前遍歷的值為: 22
-- 當前遍歷的值為: 24
-- 當前遍歷的值為: 26
-- 當前遍歷的值為: 28
-- 當前遍歷的值為: 30
-- Configuring done
-- Generating done
-- Build files have been written to: /home/robin/abc/a/build

方法3

foreach(<loop_var> IN [LISTS [<lists>]] [ITEMS [<items>]])
  1. IN:關鍵字,表示在 xxx 里邊
  2. LISTS:關鍵字,對應的是列表list,通過set、list可以獲得
  3. ITEMS:關鍵字,對應的也是列表
  4. loop_var:存儲每次循環取出的值
cmake_minimum_required(VERSION 3.2)
project(test)
# 創建 list
set(WORD a b c d)
set(NAME ace sabo luffy)
# 遍歷 list
foreach(item IN LISTS WORD NAME)message(STATUS "當前遍歷的值為: ${item}" )
endforeach()

結果:

$ cd build/
$ cmake ..
-- 當前遍歷的值為: a
-- 當前遍歷的值為: b
-- 當前遍歷的值為: c
-- 當前遍歷的值為: d
-- 當前遍歷的值為: ace
-- 當前遍歷的值為: sabo
-- 當前遍歷的值為: luffy
-- Configuring done
-- Generating done
-- Build files have been written to: /home/robin/abc/a/build

接下來看另外一種方式:

cmake_minimum_required(VERSION 3.2)
project(test)set(WORD a b c "d e f")
set(NAME ace sabo luffy)
foreach(item IN ITEMS ${WORD} ${NAME})message(STATUS "當前遍歷的值為: ${item}" )
endforeach()

遍歷過程中將關鍵字LISTS改成了ITEMS,后邊跟的還是一個或者多個列表,只不過此時需要通過${}將列表中的值取出。其輸出的信息和上一個例子是一樣的。

方法4

foreach(<loop_var>... IN ZIP_LISTS <lists>)
  1. loop_var:存儲每次循環取出的值,可以根據要遍歷的列表的數量指定多個變量,用于存儲對應的列表當前取出的那個值。
    1. 如果指定了多個變量名,它們的數量應該和列表的數量相等
    2. 如果只給出了一個 loop_var,那么它將一系列的 loop_var_N 變量來存儲對應列表中的當前項,也就是說 loop_var_0 對應第一個列表,loop_var_1 對應第二個列表,以此類推…
    3. 如果遍歷的多個列表中一個列表較短,當它遍歷完成之后將不會再參與后續的遍歷(因為其它列表還沒有遍歷完)。
  2. IN:關鍵字,表示在 xxx 里邊
  3. ZIP_LISTS:關鍵字,對應的是列表list,通過set 、list可以獲得
cmake_minimum_required(VERSION 3.17)
project(test)
# 通過list給列表添加數據
list(APPEND WORD hello world "hello world")
list(APPEND NAME ace sabo luffy zoro sanji)
# 遍歷列表
foreach(item1 item2 IN ZIP_LISTS WORD NAME)message(STATUS "當前遍歷的值為: item1 = ${item1}, item2=${item2}" )
endforeach()message("=============================")
# 遍歷列表
foreach(item  IN ZIP_LISTS WORD NAME)message(STATUS "當前遍歷的值為: item1 = ${item_0}, item2=${item_1}" )
endforeach()

結果:

$ cd build/
$ cmake ..
-- 當前遍歷的值為: item1 = hello, item2=ace
-- 當前遍歷的值為: item1 = world, item2=sabo
-- 當前遍歷的值為: item1 = hello world, item2=luffy
-- 當前遍歷的值為: item1 = , item2=zoro
-- 當前遍歷的值為: item1 = , item2=sanji
=============================
-- 當前遍歷的值為: item1 = hello, item2=ace
-- 當前遍歷的值為: item1 = world, item2=sabo
-- 當前遍歷的值為: item1 = hello world, item2=luffy
-- 當前遍歷的值為: item1 = , item2=zoro
-- 當前遍歷的值為: item1 = , item2=sanji
-- Configuring done (0.0s)
-- Generating done (0.0s)
-- Build files have been written to: /home/robin/abc/a/build

2.2 while

while(<condition>)<commands>
endwhile()

while循環比較簡單,只需要指定出循環結束的條件即可。

cmake_minimum_required(VERSION 3.5)
project(test)
# 創建一個列表 NAME
set(NAME luffy sanji zoro nami robin)
# 得到列表長度
list(LENGTH NAME LEN)
# 循環
while(${LEN} GREATER  0)message(STATUS "names = ${NAME}")# 彈出列表頭部元素list(POP_FRONT NAME)# 更新列表長度list(LENGTH NAME LEN)
endwhile()

結果:

$ cd build/
$ cmake ..
-- names = luffy;sanji;zoro;nami;robin
-- names = sanji;zoro;nami;robin
-- names = zoro;nami;robin
-- names = nami;robin
-- names = robin
-- Configuring done (0.0s)
-- Generating done (0.0s)
-- Build files have been written to: /home/robin/abc/a/build

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/904541.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/904541.shtml
英文地址,請注明出處:http://en.pswp.cn/news/904541.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

【網絡編程】二、UDP網絡套接字編程詳解

文章目錄 前言Ⅰ. UDP服務端一、服務器創建流程二、創建套接字 -- socketsocket 屬于什么類型的接口???socket 是被誰調用的???socket 底層做了什么???和其函數返回值有沒有什么關系??? 三、綁定對應端口號、IP地址到套接字 -- bind四、數據的發送和接收 -- sendto…

準確--Notepad++ 實用的插件介紹

Notepad 提供了很多實用的插件&#xff0c;可以極大地提升編程和文本編輯的效率。以下是一些常用且有用的插件介紹&#xff1a; 1. NPP Export 功能&#xff1a;可以將打開的文件導出為 HTML 或 RTF 格式&#xff0c;方便生成漂亮的代碼文檔。用途&#xff1a;適合需要將代碼…

[20250507] AI邊緣計算開發板行業調研報告 ??(2024年最新版)?

[20250507] AI邊緣計算開發板行業調研報告 ??(2024年最新版&#xff09;? 一、行業背景?? 隨著物聯網設備激增與AI模型輕量化&#xff0c;邊緣計算成為AI落地核心場景。AI邊緣計算開發板&#xff08;Edge AI Board&#xff09;作為硬件載體&#xff0c;需滿足??低延遲…

傳輸層協議 1.TCP 2.UDP

傳輸層協議 1.TCP 2.UDP TCP協議 回顧內容 傳輸層功能&#xff1a;定義應用層協議數據報文的端口號&#xff0c;流量控制對原始數據進行分段處理 傳輸層所提供服務 傳輸連接服務數據傳輸服務&#xff1a;流量控制、差錯控制、序列控制 一、傳輸層的TCP協議 1.面向連接的…

LVGL -meter的應用

1 meter介紹 lv_meter 是 LVGL v8 引入的一種圖形控件&#xff0c;用于創建儀表盤樣式的用戶界面元素&#xff0c;它可以模擬像速度表、電壓表、溫度表這類模擬表盤。它通過可視化刻度、指針、顏色弧線等來展示數值信息&#xff0c;是一種非常直觀的數據展示控件。 1.1 核心特…

GoFly企業版框架升級2.6.6版本說明(框架在2025-05-06發布了)

前端框架升級說明&#xff1a; 1.vue版本升級到^3.5.4 把"vue": "^3.2.40",升級到"vue": "^3.5.4"&#xff0c;新版插件需要時useTemplateRef,所以框架就對齊進行升級。 2.ArcoDesign升級到2.57.0&#xff08;目前最新2025-02-10&a…

阿里聯合北大開源數字人項目FantasyTalking,輸出內容更加動態化~

簡介 FantasyTalking 的核心目標是從單一靜態圖像、音頻&#xff08;以及可選的文本提示&#xff09;生成高保真、連貫一致的說話肖像。研究表明&#xff0c;現有方法在生成可動畫化頭像時面臨多重挑戰&#xff0c;包括難以捕捉細微的面部表情、整體身體動作以及動態背景的協調…

基于nnom的多選擇器

核心組件 元件類型目的接口STM32F103CB微控制器主處理單元-MPU60506 軸 IMU移動偵測I2C 接口W25Q64 系列閃存信號和配置存儲SPI 系列按鈕用戶輸入模式選擇和激活GPIO &#xff08;通用輸出&#xff09;搭載了LED用戶反饋系統狀態指示GPIO &#xff08;通用輸出&#xff09;RT6…

Redis中6種緩存更新策略

Redis作為一款高性能的內存數據庫&#xff0c;已經成為緩存層的首選解決方案。然而&#xff0c;使用緩存時最大的挑戰在于保證緩存數據與底層數據源的一致性。緩存更新策略直接影響系統的性能、可靠性和數據一致性&#xff0c;選擇合適的策略至關重要。 本文將介紹Redis中6種緩…

項目優先級頻繁變動,如何應對?

項目優先級頻繁變動是許多公司和團隊在工作中常遇到的挑戰。 這種情況通常由業務需求變化、市場壓力或高層決策調整等因素引起&#xff0c;常常讓團隊成員感到困惑和不安。首先&#xff0c;制定明確的優先級管理框架是應對項目優先級變動的基礎&#xff0c; 通過清晰的優先級排…

屏蔽力 | 在復雜世界中從內耗到成長的轉變之道

注&#xff1a;本文為“屏蔽力”相關文章合輯。 略作重排&#xff0c;未全整理。 世上的事再復雜&#xff0c;不外乎這三種 原創 小鹿 讀者 2022 年 12 月 02 日 18 : 27 甘肅 文 / 小鹿 在這世上&#xff0c;每天都有大事小事、瑣事煩事。我們總為世事奔波忙碌&#xff0c;…

[數據處理] 3. 數據集讀取

&#x1f44b; 你好&#xff01;這里有實用干貨與深度分享?? 若有幫助&#xff0c;歡迎&#xff1a;? &#x1f44d; 點贊 | ? 收藏 | &#x1f4ac; 評論 | ? 關注 &#xff0c;解鎖更多精彩&#xff01;? &#x1f4c1; 收藏專欄即可第一時間獲取最新推送&#x1f514;…

IIS配置SSL

打開iis 如果搜不到iis&#xff0c;要先開 再搜就打得開了 cmd中找到本機ip 用http訪問本機ip 把原本的http綁定刪了 再用http訪問本機ip就不行了 只能用https訪問了

RabbitMQ的交換機

一、三種交換機模式 核心區別對比?? ??特性????廣播模式&#xff08;Fanout&#xff09;????路由模式&#xff08;Direct&#xff09;????主題模式&#xff08;Topic&#xff09;????路由規則??無條件復制到所有綁定隊列精確匹配 Routing Key通配符匹配…

(2025,AR,NAR,GAN,Diffusion,模型對比,數據集,評估指標,性能對比)文本到圖像的生成和編輯:綜述

【本文為我在去年完成的綜述&#xff0c;因某些原因未能及時投稿&#xff0c;但本文仍能為想要全面了解文本到圖像的生成和編輯的學習者提供可靠的參考。目前本文已投稿 ACM Computing Surveys。 完整內容可在如下鏈接獲取&#xff0c;或在 Q 群群文件獲取。 中文版為論文初稿&…

MCU怎么運行深度學習模型

Gitee倉庫 git clone https://gitee.com/banana-peel-x/freedom-learn.git項目場景&#xff1a; 解決面試時遺留的問題&#xff0c;面試官提了兩個問題&#xff1a;1.單片機能跑深度學習的模型嗎&#xff1f; 2.為什么FreeRTOS要采用SVC去觸發第一個任務&#xff0c;只用Pend…

多模態學習(一)——從 Image-Text Pair 到 Instruction-Following 格式

前言 在多模態任務中&#xff08;例如圖像問答、圖像描述等&#xff09;&#xff0c;為了使用指令微調&#xff08;Instruction Tuning&#xff09;提升多模態大模型的能力&#xff0c;我們需要構建成千上萬條**指令跟隨&#xff08;instruction-following&#xff09;**格式的…

MySQL基礎關鍵_011_視圖

目 錄 一、說明 二、操作 1.創建視圖 2.創建可替換視圖 3.修改視圖 4.刪除視圖 5.對視圖內容的增、刪、改 &#xff08;1&#xff09;增 &#xff08;2&#xff09;改 &#xff08;3&#xff09;刪 一、說明 只能將 DQL 語句創建為視圖&#xff1b;作用&#xff1a; …

『深夜_MySQL』數據庫操作 字符集與檢驗規則

2.庫的操作 2.1 創建數據庫 語法&#xff1a; CREATE DATABASE [IF NOT EXISTS] db_name [create_specification [,create_specification]….]create_spcification:[DEFAULT] CHARACTER SET charset_nam[DEFAULT] COLLATE collation_name說明&#xff1a; 大寫的表示關鍵字 …

Spark jdbc寫入崖山等國產數據庫失敗問題

隨著互聯網、信息產業的大發展、以及地緣政治的變化,網絡安全風險日益增長,網絡安全關乎國家安全。因此很多的企業,開始了國產替代的腳步,從服務器芯片,操作系統,到數據庫,中間件,逐步實現信息技術自主可控,規避外部技術制裁和風險。 就數據庫而言,目前很多的國產數據…