Любая функция, которая состоит только из оператора возврата, может быть объявлена constexpr
и, таким образом, позволит выполнять оценку во время компиляции, если все аргументы constexpr
и в ее теле вызываются только функции constexpr
. Есть ли причина не объявлять любую такую функцию constexpr
?
Пример:
constexpr int sum(int x, int y) { return x + y; }
constexpr i = 10;
static_assert(sum(i, 13) == 23, "sum correct");
Может ли кто-нибудь предоставитьпример, где объявление функции constexpr
принесет какой-либо вред?
Некоторые первоначальные мысли:
Даже если не должно быть веских оснований для объявления функции не constexpr
Я мог бы себе представить, что ключевое слово constexpr
играет переходную роль: его отсутствие в коде, не требующем оценки во время компиляции, позволило бы компиляторам, которые не реализуют оценки во время компиляции, по-прежнему компилировать этот код (но надежно терпеть неудачу прикод, который нуждается в их объяснении с использованием constexpr
).
Но что я не понимаю: если не должно быть веской причины для того, чтобы когда-либо объявлять функцию не constexpr
, то почему бы не каждая функция в стандартной библиотеке объявлена constexpr
?(Вы не можете утверждать, что это еще не сделано, потому что еще не было достаточно времени, чтобы сделать это, потому что делать это для all не составляет никакого труда - вопреки решению для каждой отдельной функции, если сделать этоconstexpr
или нет.) --- Мне известно, что N2976 сознательно не требует cstrs для многих стандартных типов библиотек, таких как контейнеры, поскольку это было бы слишком ограничивающим для возможных реализаций.Давайте исключим их из аргумента и просто удивимся: если тип в стандартной библиотеке действительно имеет constexpr
cstr, почему не каждая функция, работающая с ним, объявляется constexpr
?
В большинстве случаев вы также не можетеутверждают, что вы можете предпочесть не объявлять функцию constexpr
просто потому, что вы не предполагаете никакого использования во время компиляции: потому что, если другие evtl.будет использовать ваш код, они могут увидеть такое использование, что вы этого не сделаете.(Но, конечно, для типов признаков и тому подобного.)
Так что я думаю, что должна быть веская причина и хороший пример для того, чтобы сознательно не объявлять функцию constexpr
?
(Под «каждой функцией» я всегда имею в виду: каждая функция, которая удовлетворяет требованиям для constexpr
, т. е. определяется как один оператор возврата, принимает только аргументы типов с constexpr cstrs и вызывает только constexpr
функции.)
Вопрос Почему std::forward
отбрасывает constexpr
-ness? является частным случаем этого.