cmake教程5-macro巨集定義以及傳遞引數給原始檔
引入在C++程式中我們經常見到如下,兩個問題:
1. 輸出當前程式的版本號
2. 通過cmake新增macro巨集定義 出入到原始檔,例如在編譯opencv/caffe的時候,我們通過cmake -DUSE_CUDA=ON/OFF來確定,是否使用cuda.
問題cmake中如何實現上述兩個功能的呢?
至於問題1:
我們可能想到直接在標頭檔案中定義,這樣也可以,但是如果直接在cmake中定義,然後傳遞給程式讀取生成更加靈活。
至於問題2:
可以在cmake中通過option函式
以及add_definitions函式
來實現。
cmake 傳遞版本號給原始檔
首先定義demo11Config.h.in標頭檔案接受CMakeLists.txt傳遞來的版本號引數,檔案內容如下:
// the configured options and settings for demo11
#define demo11_VERSION_MAJOR @[email protected]
#define demo11_VERSION_MINOR @[email protected]
demo11.cpp程式碼如下:
#include <stdio.h>
// demoConfig.h檔案是cmake生成的
#include "demoConfig.h"
int main(int argc, char* argv[]){
printf("%s version: %d.%d \n", argv[0], demo11_VERSION_MAJOR, demo11_VERSION_MINOR);
}
注意的是demoConfig.h是生成的在專案結構中並不存在,專案目錄如下:
CMakeLists.txt
如下:
cmake_minimum_required(VERSION 3.5)
project(demo11)
# The version number
set(demo11_VERSION_MAJOR 1)
set(demo11_VERSION_MINOR 0 )
# configure a header file to pass some of the CMake settings to
# source code(demo11Config.h.in), the file demoConfig.h does't exists
configure_file(
"${PROJECT_SOURCE_DIR}/demo11Config.h.in"
"${PROJECT_BINARY_DIR}/demoConfig.h"
)
# add the binary tree to the search path for include files
# so that we will find demoConfig.h
include_directories("${PROJECT_BINARY_DIR}")
# add the exectuable
add_executable(demo11 demo11.cpp)
cmake 編譯如下:
root@xy:~/cmake_practice/cmake_build/build_demo11# cmake ../../cmake_tuorial/demo11/
-- The C compiler identification is GNU 5.4.0
可以看到生產了demoConfig.h:
drwxr-xr-x 3 root root 4096 Jun 29 08:42 ./
........
-rw-r--r-- 1 root root 112 Jun 29 08:42 demoConfig.h
-rw-r--r-- 1 root root 4865 Jun 29 08:42 Makefile
demoConfig.h內容如下:
// the configured options and settings for demo11
#define demo11_VERSION_MAJOR 1
#define demo11_VERSION_MINOR 0
make & run,輸出如下:
root@xy:~/cmake_practice/cmake_build/build_demo11# ./demo11
./demo11 version: 1.0
新增macro到src檔案中(add_definitions/option)
本例項在cmake中新增macro定義到原始檔中,從而選擇使用不同的lib 模組函式.
專案目錄如下:demo12.cpp根據cmake定義的macro USE_SPECIFIED決定使用模組SpecifiedFun(特定的函式),還是模組CommonFun(一般的函式).
兩個模組都只有一個函式showSelectedFun,主要是輸出呼叫了哪個函式.
模組CommonFun,內容如下:
void showSelectedFun(){
std::cout<<"Select to use common function"<<std::endl;
}
對應的cmake如下:
add_library(common_fun CommonFun.cpp)
模組SpecifiedFun,內容如下:
void showSelectedFun(){
std::cout<<"Select to use specified function"<<std::endl;
}
對應的cmake如下:
add_library(specified_fun SpecifiedFun.cpp)
主CMakeLists.txt內容如下, 主要是通過option USE_SPECIFIED ON/OFF
來決定使用新增macro add_definitions(-DUSE_SPECIFIED)
:
cmake_minimum_required(VERSION 3.5)
# should we use specified function
# if not set, then will use common function
option(USE_SPECIFIED "select to use specified function" ON)
# select to use specified function, or common function
message("USE_SPECIFIED is ${USE_SPECIFIED}")
if(USE_SPECIFIED)
add_definitions(-DUSE_SPECIFIED)
include_directories("${PROJECT_SOURCE_DIR}/SpecifiedFun")
add_subdirectory(SpecifiedFun)
set(EXTRA_LIBS ${EXTRA_LIBS} specified_fun)
message("select to use specified function, lib is: ${EXTRA_LIBS}")
else()
include_directories("${PROJECT_SOURCE_DIR}/CommonFun")
add_subdirectory(CommonFun)
set(EXTRA_LIBS ${EXTRA_LIBS} common_fun)
message("select to use common function, lib is: ${EXTRA_LIBS}")
endif(USE_SPECIFIED)
add_executable(demo12 demo12.cpp)
target_link_libraries(demo12 ${EXTRA_LIBS})
首先編譯不使用USE_SPECIFIED
即 USE_SPECIFIED=OFF
root@xy:~/tmp/demo12/build# cmake -DUSE_SPECIFIED=OFF ..
..........
USE_SPECIFIED is OFF
select to use common function, lib is: common_fun
-- Configuring done
-- Generating done
-- Build files have been written to: /home/xy/tmp/demo12/build
編譯make:
root@xy:~/tmp/demo12/build# make
Scanning dependencies of target common_fun
[ 25%] Building CXX object CommonFun/CMakeFiles/common_fun.dir/CommonFun.cpp.o
[ 50%] Linking CXX static library libcommon_fun.a
[ 50%] Built target common_fun
Scanning dependencies of target demo12
[ 75%] Building CXX object CMakeFiles/demo12.dir/demo12.cpp.o
[100%] Linking CXX executable demo12
[100%] Built target demo12
執行:
root@xy:~/tmp/demo12/build# ./demo12
Select to use common function
使用macro USE_SPECIFIED直接使用cmake .. 即可
接下來的步驟一樣就不重複了
相關推薦
cmake教程5-macro巨集定義以及傳遞引數給原始檔
引入在C++程式中我們經常見到如下,兩個問題: 1. 輸出當前程式的版本號 2. 通過cmake新增macro巨集定義 出入到原始檔,例如在編譯opencv/caffe的時候,我們通過cmake -DUSE_CUDA=ON/OFF來確定,是否使用c
unity自定義巨集定義以及常用自帶的巨集定義
如下是系統有的巨集, //如果你的平臺已經被你switch platform 你的那個平臺過後,對應的輸出列印是彩色的,否則是灰色的 #if UNITY_IPHONE Debug.Log("UNITY_IPHONE"); #elif UNITY_ANDROI
JSP 關於的使用以及傳遞引數
首先說明一下,<jsp:forward>是動作指令。 我覺得有必要對jsp中的幾個指令總結一下了 jsp中的指令分為兩大類,編譯指令和動作指令。 編制指令 <%@ i
Unity3D和IOS的互動教程——通過URL啟動APP並傳遞引數
最近專案(麻將手遊)中遇到這樣一個需求:在建立一個私人房後通過ShareSDK分享一個連線到微信,點選這個連線後設備將跳轉至下載頁面或是啟動APP並直接進入到指定房間。由於目前沒有原生IOS的開發經驗,在發揮面向百度程式設計師的特長之後,寫出來下面的方案並用於專案中,實測可
Makefile(或者shell)的變數通過gcc的-D巨集定義選項傳遞給C原始檔
當make巢狀呼叫時,上層Makefile中定義的變數會以系統環境變數的方式傳遞到下層的Makefile中。這裡的系統環境變數與本makefile中定義的變數的關係有點類似於全域性變數與區域性變數的關係。預設情況下,只有通過命令列設定的變數會被傳遞。而定義在檔案中的變數,如果要向下層Makefile傳遞,則
struts2在action中傳遞引數給頁面的方法
由於在Action中並不能直接誒訪問Servlet API,但它提供了相關類ActionContext來訪問HttpServletRequest、HttpSession和ServletContext,所以在向前端頁面傳值的方法就出現了多樣化。一般我們經常使用的就是通過request、session來
後端接受前端的引數型別(前端傳遞引數給後端)
引數傳遞形式: Get請求 引數放到url後面,用&隔開即可 Post請求 傳遞的引數的形式就比較多了。。。。 一、普通的鍵值對引數: get請求實質也是鍵值對的形式 二、list傳值 也可以把list物件放到物件裡面
layui使用button按鈕 點擊出現子彈層 彈層中載入表單,並傳遞引數給父彈出層
在父層中增加button按鈕和隱藏域接收子彈出層傳遞的值 <button id="btnMenuTree" type="button" class="layui-btn layui-btn-radius layui-btn-normal layui-btn-xs">選擇</bu
內部類怎麼傳遞引數給外部類???
參考連結:http://wendal.net/404.html傳入: //匿名內部類,只能訪問final的本地變數及方法引數 public void addUser(final String name, String passwd, final String userTyp
以form表單的形式傳遞引數給rest介面
/** * 以傳統form表單的方式提交引數(並不是以json格式提交) * * @param url 提交的rest url * @param paramMap body引數 * @param r
(三)在TestNG中傳遞引數給方法使用
TestNG允許我們在Test Method 以及 @Before/After類註解 、 @Factory類註解註解的方法中傳入引數引數傳遞的方式有兩種,一種是藉助xml檔案配置,一種是以編碼的方式傳遞引數。一、藉助xml檔案配置:1.在方法上使用@Parameters({"
android原生webview中呼叫JS方法並傳遞引數給JS遇到的問題
在使用webview時,需要給JS傳遞一個引數,之前前端同事把JS方法內容和html內容分離了,所以在使用下面的方法的時候一直顯示方法未定義[INFO:CONSOLE(1)] "Uncaught ReferenceError: load is not defined", s
JSP傳遞引數給servlet的三種方法
Jsp與Servlet之間的傳值有兩種,一種是Jsp傳值給Sevlet,另一種是Servlet傳值給Jsp;使用request、response物件完成傳值,具體實現如下:1.JSP傳值給ServletJSP傳值給Servlet有幾種形式:Form表單傳值,url傳值,其他方式傳值a、form表單傳值:JSP
[JNI]開發之旅(8)傳遞引數給JNI函式
本節將介紹在JNI程式設計中如何傳遞引數和返回值。 首先要強調的是,native方法不但可以傳遞Java的基本型別做引數,還可以傳遞更復雜的型別,比如String,陣列,甚至自定義的類。jni.h中定義了很多介面供我們操作。 其實在前面章節的例子中,我們已經
typedef詳解以及與巨集定義#define的區別
typedef是在計算機程式語言中用來為複雜的宣告定義簡單的別名,它與巨集定義有些差異。它本身是一種儲存類的關鍵字,與auto、extern、mutable、static、register等關鍵字不能出現在同一個表示式中; typedef 中文解釋:宣告型別; typedef為C語言
flask框架模板巨集macro的定義及使用
示例1 (index.html) <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title&g
Python 函式定義以及引數傳遞
Python 函式定義以及引數傳遞1.函式定義#形如def func(args...): doSomething123以關鍵字def 開頭,後面是函式名和引數下面是函式處理過程。 舉例: def add( a, b ): return a+b12引數可以設定預設值,如: def add( a, b=10
強大的巨集定義(macro)
事件分發:(global.h) #pragma once #include <map> #include <functional> #include <Windows.h> #include <tchar.h> #include <v
生產環境的開源容器管理平臺--Rancher入門教程 5 自定義Catalog工具
Rancher是一個用於部署和管理生產環境的容器的開源平臺,它與Kubernetes/Mesos/Docker Swarm進行整合。使得在任何硬體環境上容器化應用變得觸手可及。在這個系列的教程中我們將會學習如何使用rancher, 上篇文章介紹瞭如何在rancher中新增自定義的catal
Alex 的 Hadoop 菜鳥教程: 第5課 YARN 安裝以及helloworld (基於centos的CDH)
原帖地址:http://blog.csdn.net/nsrainbow/article/details/36627675 新老MapReduce的比較 說到YARN肯定要先說下老的MapReduce MRv1 (MapReduce v1)的架構圖 從上圖中可以清楚的看出