#c #visual-c #cmake
#c #visual-c #cmake
Вопрос:
Я могу установить CMAKE_CXX_STANDARD
значение 17
для получения /std:c 17
, но я не могу установить его latest
, не так ли? Я думаю, я могу просто перебрать его с помощью
if (MSVC)
add_compiler_options(/std:c latest)
endif()
конечно, но есть ли идиоматический способ получить /std:c latest
, может быть, даже не зависящий от цепочки инструментов?
РЕДАКТИРОВАТЬ Зачем кому-то это нужно? В отличие от Clang и GCC, MSVC, похоже, не определяет /std:c 2a
включение функций post-C 17. Он просто использует /std:c latest
для этого. Если я создаю базу кода с набором известных компиляторов, я знаю, какие функции C 20 я могу использовать, но мне нужно указать системе сборки включить все, на что способен каждый компилятор.
Комментарии:
1. Я не знаю ни одного компилятора (или набора инструментов), который предоставлял бы такую вещь. Большинство поставщиков ожидают, что пользователь будет знать и намеренно выбирать стандарт, для которого они создают (и по умолчанию использовать стандарт, для которого их поддержка стабильна и почти завершена). Поскольку последняя версия часто является нестабильной и нестабильной для разработки, выбор последней версии действительно предназначен для опытных и продвинутых разработчиков, которые хотят и могут справиться с неполными или неправильными реализациями языка или библиотеки. И эти разработчики, вероятно, будут точно знать, какую версию стандарта они хотят использовать.
2. Переменная
CMAKE_CXX_STANDARD
действительно является единственным «независимым от цепочки инструментов» способом настройки используемой версии C . И, к сожалению, он допускает только определенные предопределенные значения. Кроме того, ни у GCC, ни у Clang нет «последней» стандартной опции IIRC.3. Хотя я понимаю вашу мотивацию для использования этой функции, это серьезно подорвет переносимость данной кодовой базы и системы сборки CMake. Определение «latest» будет значительно меняться между различными компиляторами и даже версиями компилятора. Лучше четко указать, какую версию вы хотите.
4. @Someprogrammerdude добавляя обоснование к вопросу, я понял, что Clang и GCC просто используют другой способ включить latest. Для этих компиляторов вы говорите
-std=c 1z
или-std=c 2a
, и они остаются навсегда, в конечном итоге становясь псевдонимами для-std=c 17
и-std=c 20
, соответственно/std:c latest
, otoh, является движущейся целью. После C 20 это станет тем, что, скорее всего, вызовут GCC и Clang-std=c 2b
. Я думаю, что мне больше нравится GCC / Clang по причинам, которые Ботье и Питер правильно указали в своих комментариях.
Ответ №1:
До CMake 3.20.3, если вы попросите C 20, используя set(CMAKE_CXX_STANDARD 20)
, вы получите -std:c latest
. Доказательство:
if (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.12.25835)
set(CMAKE_CXX20_STANDARD_COMPILE_OPTION "-std:c latest")
set(CMAKE_CXX20_EXTENSION_COMPILE_OPTION "-std:c latest")
endif()
(из Modules/Compiler/MSVC-CXX.cmake в исходных текстах cmake)
ОБНОВЛЕНИЕ: начиная с CMake 3.20.4, set(CMAKE_CXX_STANDARD 20)
вы получаете -std:c 20
, поэтому вам нужно set(CMAKE_CXX_STANDARD 23)
получить -std:c latest
— при условии, что ваша версия компилятора MSVC — 16.11 Preview 1 или более поздняя (см. cmake commit 3aaf1d91bf353).
Ответ №2:
Предполагая, что вы используете компилятор, который уже совместим с C 20, и вы не хотите указывать «if» и дополнительное назначение, как это было сделано в предыдущем ответе, это стандартный способ поместить последнюю версию C в CMake при использовании Visual Studio или другого компилятора.
target_compile_features(${PROJECT_NAME} PRIVATE cxx_std_20)
Вот список функций, поддерживаемых CMake в случае C CMAKE_CXX_KNOWN_FEATURES.
Ответ №3:
Поддерживаемые значения: 98, 11, 14, 17 и 20.
Согласно документам CMake