I'd like to use constexpr
versions of standard <cmath>
functions like exp
, log
, pow
in a portable way. I currently have a non-portable solution g++
treats these functions as constexpr
- a non-compliant extension of C++, but I am concerned about portability and future-proofing (I imagine that this extension might one day be removed from g++
).
I am interested in constexpr
versions of these functions, not template metaprograms - I want the same functionality to be available both at compile time and runtime. I do not need C compatibility, but I do need fast implementations - naive implementations such as Taylor Series expansions would be too slow.
How can I implement such functionalities? I am specifically interested in exp
, log
, and pow
Some tangentially related things I've learned from my research
constexpr
because they must have side-effects (e.g. setting errno
) to maintain C compatibilityconstexpr
, but as of C++14, this is prohibited (per the first answer to this question and the answer to this question). This is part of the reason that I am concerned that the functions may not be constexpr
in future versions of g++
g++
's implementation of each math function foo
just calls a built-in function __builtin_foo
, which is treated as constexpr
. I could perhaps start calling the __builtin_foo
functions rather than the foo
functions - these might remain constexpr
in future versions of g++
even if the corresponding foo
functions are made compliant - but this only helps with future-proofing, not with portability.constexpr indicates that the value, or return value, is constant and, where possible, is computed at compile time. A constexpr integral value can be used wherever a const integer is required, such as in template arguments and array declarations.
constexpr functions will be evaluated at compile time when all its arguments are constant expressions and the result is used in a constant expression as well.
So you should definitely use static constexpr in your example. However, there is one case where you wouldn't want to use static constexpr . Unless a constexpr declared object is either ODR-used or declared static , the compiler is free to not include it at all.
A static constexpr variable has to be set at compilation, because its lifetime is the the whole program. Without the static keyword, the compiler isn't bound to set the value at compilation, and could decide to set it later.
Have you ever watch Sprout's implementaion?
Sprout is header-only library that provide C++11/14 constexpr based Containers, Algorithms, Random numbers, Parsing, Ray tracing, Synthesizer, and others.
https://github.com/bolero-MURAKAMI/Sprout/tree/master/sprout/math
Check out gcem
which provides compile time mathematical functions. They can be called just like the ones in std
but using the gcem
prefix.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With