В C++ существует compile-time (константность на этапе компиляции) и link-time (на этапе компоновки) константность.
const переменная — это объект, который нельзя изменить после инициализации. Но const не всегда гарантирует, что значение известно на этапе компиляции; оно может быть вычислено только во время выполнения.constexpr — гарантирует, что выражение или функция будет вычислено уже на этапе компиляции.Пример:
const int x = time(0); // const, но НЕ constexpr: значение вычисляется во времени выполнения constexpr int y = 2 + 2; // constexpr: известно на этапе компиляции constexpr int square(int x) { return x * x; } int arr[square(3)]; // размер массива — выражение времени компиляции
Используйте constexpr для константных выражений, которые должны быть доступны компилятору, например, для размерами массива или шаблонных параметров.
Может ли функция, объявленная как constexpr, вызываться с не-константными аргументами?
Ответ: Да! Если аргументы известны во время компиляции, результат будет вычислен на этапе компиляции. Если аргументы известны только во время выполнения, функция будет вычисляться как обычная.
constexpr int double_val(int x) { return x * 2; } int val = std::rand(); int result = double_val(val); // Вызовится на этапе run-time
История
Один из модулей задавал размер массива через
const int, рассчитывая, что это константа времени компиляции. На другом компиляторе это вызвало ошибку, потому что значение было вычислено на run-time, и размер массива не соответствовал стандарту.
История
В расчёте хешей компилятор не мог оптимизировать вычисления, потому что использовалась
constпеременная, а неconstexpr. Итог: снижение производительности более чем в 2 раза на новых релизах.
История
При миграции на современные стандарты перепутали ключевые слова и объявили функцию как
const, а неconstexpr, из-за чего нельзя было использовать результат в compile-time выражениях шаблонов. Быстрая диагностика показала ошибку, но на ревью она ушла в master.