你的辦法將 - 如@Tsyvarev曾評論 - 絕對很好,只是因爲你已經要求在C進行「新」辦法這裏是你的代碼會翻譯什麼:
cmake_minimum_required(VERSION 3.8)
project(HelloWorld)
string(
APPEND _opts
"$<IF:$<CXX_COMPILER_ID:MSVC>,"
"/W4;$<$<CONFIG:RELEASE>:/O2>,"
"-Wall;-Wextra;-Werror;"
"$<$<CONFIG:RELEASE>:-O3>"
"$<$<CXX_COMPILER_ID:Clang>:-stdlib=libc++>"
">"
)
add_compile_options("${_opts}")
add_executable(HelloWorld "main.cpp")
target_compile_features(HelloWorld PUBLIC cxx_lambda_init_captures)
你拿add_compile_options()
和 - as @ Al.G。已評論 - 「使用髒generator expressions」。
有發電機表達式的一些缺點:
- 很有幫助
$<IF:...,...,...>
表達只是CMake的版本> = 3.8
- 你必須把它寫在一行可用。爲了避免它,我使用了
string(APPEND ...)
,您也可以使用它來「優化」您的set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ...
調用。
- 這很難閱讀和理解。例如。需要分號才能使其成爲編譯選項列表(否則CMake會引用它)。
所以最好使用一個更具可讀性和向後兼容的方式與add_compile_options()
:
if(MSVC)
add_compile_options("/W4" "$<$<CONFIG:RELEASE>:/O2>")
else()
add_compile_options("-Wall" "-Wextra" "-Werror" "$<$<CONFIG:RELEASE>:-O3>")
if("${CMAKE_CXX_COMPILER_ID}" STREQUAL "Clang")
add_compile_options("-stdlib=libc++")
else()
# nothing special for gcc at the moment
endif()
endif()
是的,你沒有明確指定C++標準了,你剛纔命名C++ feature代碼/目標確實取決於target_compile_features()
調用。
在這個例子中,我選擇了cxx_lambda_init_captures
,舊的GCC編譯器提供以下錯誤(作爲一個例子會發生什麼,如果編譯器不支持此功能):
The compiler feature "cxx_lambda_init_captures" is not known to CXX compiler
"GNU"
version 4.8.4.
而且你需要寫一個包裝腳本構建與"single configuration" makefile generator或多個配置作爲Visual Studio使用"multi configuration" IDE。
下面是引用的例子:
所以,我測試了Open Folder
Visual Studio中的下列2017年CMake的支持,在結合此示例爲cl,clang和mingw編譯器:
CMakeSettings.json
{
// See https://go.microsoft.com//fwlink//?linkid=834763 for more information about this file.
"configurations": [
{
"name": "x86-Debug",
"generator": "Visual Studio 15 2017",
"configurationType": "Debug",
"buildRoot": "${env.LOCALAPPDATA}\\CMakeBuild\\${workspaceHash}\\build\\${name}",
"buildCommandArgs": "-m -v:minimal",
},
{
"name": "x86-Release",
"generator": "Visual Studio 15 2017",
"configurationType": "Release",
"buildRoot": "${env.LOCALAPPDATA}\\CMakeBuild\\${workspaceHash}\\build\\${name}",
"buildCommandArgs": "-m -v:minimal",
},
{
"name": "Clang-Debug",
"generator": "Visual Studio 15 2017",
"configurationType": "Debug",
"buildRoot": "${env.LOCALAPPDATA}\\CMakeBuild\\${workspaceHash}\\build\\${name}",
"cmakeCommandArgs": "-T\"LLVM-vs2014\"",
"buildCommandArgs": "-m -v:minimal",
},
{
"name": "Clang-Release",
"generator": "Visual Studio 15 2017",
"configurationType": "Release",
"buildRoot": "${env.LOCALAPPDATA}\\CMakeBuild\\${workspaceHash}\\build\\${name}",
"cmakeCommandArgs": "-T\"LLVM-vs2014\"",
"buildCommandArgs": "-m -v:minimal",
},
{
"name": "GNU-Debug",
"generator": "MinGW Makefiles",
"configurationType": "Debug",
"buildRoot": "${env.LOCALAPPDATA}\\CMakeBuild\\${workspaceHash}\\build\\${name}",
"variables": [
{
"name": "CMAKE_MAKE_PROGRAM",
"value": "${projectDir}\\mingw32-make.cmd"
}
]
},
{
"name": "GNU-Release",
"generator": "Unix Makefiles",
"configurationType": "Release",
"buildRoot": "${env.LOCALAPPDATA}\\CMakeBuild\\${workspaceHash}\\build\\${name}",
"variables": [
{
"name": "CMAKE_MAKE_PROGRAM",
"value": "${projectDir}\\mingw32-make.cmd"
}
]
}
]
}
的mingw32-make.cmd
@echo off
mingw32-make.exe %~1 %~2 %~3 %~4
所以,你可以使用任何CMake的發電機從Visual Studio 2017年中,還有一些不健康的報價正在進行(截至2017年9月,mayb e稍後修復),即需要mingw32-make.cmd
中介(刪除引號)。
關於前兩點:https://cmake.org/cmake/help/v3.3/command/add_compile_options.html –
@ AI.G。謝謝。是否還有單獨的調試和釋放集,我必須通過另一級別的if_else解決?我用生成器表達式進行了一些嘗試,但我感覺這變得更不可讀。 – MikeMB
當我看到它,你既可以用髒髮電機表達式或'設置(CMAKE_CXX_FLAGS_DEBUG「$ {} CMAKE_CXX_FLAGS_DEBUG --flags」)'相當詳細的語法。在這種情況下(考慮到這些不滿意),你可以嘗試編寫一些幫助函數,將髒代碼包裝成更令人愉快的東西。 –