Связано: Функция, возвращающая constexpr, не компилируется
Я чувствую, что constexpr ограничен в полезности в С++ 11 из-за невозможности определить две функции, которые в противном случае имели бы одну и ту же подпись, но они были бы constexpr, а другие не constexpr. Другими словами, было бы очень полезно, если бы у меня был, например, конструктор constexpr std::string, который принимает только аргументы constexpr, и конструктор non-constexpr std::string для аргументов без constexpr. Другим примером может быть теоретически сложная функция, которая может быть более эффективной при использовании состояния. Вы не можете легко сделать это с помощью функции constexpr, поэтому у вас останутся два варианта: у вас есть функция constexpr, которая очень медленная, если вы передаете аргументы неконференции, или полностью откажитесь от constexpr (или напишите две отдельные функции, но вы можете не знать, какую версию вызывать).
Поэтому мой вопрос заключается в следующем:
Возможно ли, чтобы стандартная реализация С++ 11 позволяла перегружать функции на основе аргументов constexpr, или это потребовало бы обновления стандарта? Если это не разрешено, было ли это намеренно запрещено?
@NicolBolas: Скажем, у меня есть функция, которая отображает enum
в std::string
. Самый простой способ сделать это, предполагая, что мой enum
идет от 0
до n - 1
, заключается в создании массива размера n
, заполненного результатом.
Я мог бы создать static constexpr char const * []
и построить std::string
при возврате (оплачивая стоимость создания объекта std::string
при каждом вызове функции), или я могу создать static std::string const []
и вернуть значение я посмотрите, оплатив стоимость всех конструкторов std::string
при первом вызове функции. Похоже, лучшим решением было бы создать std::string
в памяти во время компиляции (аналогично тому, как это делается теперь с char const *
), но единственным способом сделать это было бы предупреждение конструктора о том, что он имеет constexpr
аргументы.
Для примера, отличного от конструктора std::string
, я думаю, что довольно просто найти пример, где, если бы вы могли игнорировать требования constexpr
(и тем самым создать функцию constexpr
), вы можете создать более эффективную функцию. Подумайте об этой теме: вопрос constexpr, почему эти две разные программы выполняются за такое разное время с g++?
Если я вызываю fib
с аргументом constexpr
, я не могу бить лучше, чем компилятор, полностью оптимизирующий вызов функции. Но если я вызываю fib
с аргументом non constexpr
, я могу захотеть, чтобы он вызывал мою собственную версию, которая реализует такие вещи, как memoization (для чего требуется состояние), поэтому я получаю время выполнения, подобное тому, что было бы моим компилятором я передал аргумент constexpr
.