GCE-Math ( G eneralized C onstant E xpression Math) es una biblioteca C++ con plantilla que permite el cálculo de funciones matemáticas en tiempo de compilación.
Características:
constexpr
de C++ 11 y es compatible con C++ 11/14/17/20.gcem::
es idéntica a la de la biblioteca estándar de C++ ( std::
).Autor : Keith O'Hara
La biblioteca se mantiene activamente y aún se está ampliando. Una lista de características incluye:
abs
, max
, min
, pow
, sqrt
, inv_sqrt
,ceil
, floor
, round
, trunc
, fmod
,exp
, expm1
, log
, log1p
, log2
, log10
y máscos
, sin
, tan
acos
, asin
, atan
, atan2
cosh
, sinh
, tanh
, acosh
, asinh
, atanh
gcd
, lcm
factorial
, binomial_coef
beta
, lbeta
, lgamma
, tgamma
, lmgamma
erf
, erf_inv
incomplete_beta
, incomplete_gamma
incomplete_beta_inv
, incomplete_gamma_inv
La documentación completa está disponible en línea:
Una versión PDF de la documentación está disponible aquí.
GCE-Math es una biblioteca de solo encabezado y no requiere bibliotecas ni utilidades adicionales (más allá de un compilador compatible con C++ 11). Simplemente agregue los archivos de encabezado a su proyecto usando:
# include " gcem.hpp "
Puede instalar GCE-Math utilizando el administrador de paquetes Conda.
conda install -c conda-forge gcem
También puede instalar la biblioteca desde el código fuente usando CMake.
# clone gcem from GitHub
git clone https://github.com/kthohr/gcem ./gcem
# make a build directory
cd ./gcem
mkdir build
cd build
# generate Makefiles and install
cmake .. -DCMAKE_INSTALL_PREFIX=/gcem/install/location
make install
Por ejemplo, /gcem/install/location
podría ser /usr/local/
.
Hay dos formas de crear el conjunto de pruebas. En sistemas similares a Unix, hay un Makefile disponible en tests/
.
cd ./gcem/tests
make
./run_tests
Con CMake, la opción GCEM_BUILD_TESTS=1
genera los Makefiles necesarios para construir el conjunto de pruebas.
cd ./gcem
mkdir build
cd build
cmake ../ -DGCEM_BUILD_TESTS=1 -DCMAKE_INSTALL_PREFIX=/gcem/install/location
make gcem_tests
cd tests
./exp.test
Puede probar la biblioteca en línea utilizando un cuaderno interactivo de Jupyter:
Las funciones de GCE-Math están escritas como plantillas de C++ con especificadores constexpr
, cuyo formato puede parecer confuso para los usuarios que no están familiarizados con la programación basada en plantillas.
Por ejemplo, la función de error gaussiana ( erf
) se define como:
template < typename T>
constexpr
return_t <T>
erf ( const T x) noexcept ;
Un conjunto de funciones constexpr
con plantilla interna implementará una expansión de fracción continua y devolverá un valor de tipo return_t<T>
. El tipo de salida (' return_t<T>
') generalmente está determinado por el tipo de entrada, por ejemplo, int
, float
, double
, long double
, etc.; cuando T
es un tipo integral, la salida se actualizará a return_t<T> = double
; de lo contrario, return_t<T> = T
Para los tipos no cubiertos por std::is_integral
, se deben utilizar refundiciones.
Para calcular 10!:
# include " gcem.hpp "
int main ()
{
constexpr int x = 10 ;
constexpr int res = gcem::factorial (x);
return 0 ;
}
Inspeccionando el código ensamblador generado por Clang 7.0.0:
push rbp
mov rbp , rsp
xor eax , eax
mov dword ptr [ rbp - 4 ], 0
mov dword ptr [ rbp - 8 ], 10
mov dword ptr [ rbp - 12 ], 3628800
pop rbp
ret
Vemos que una llamada a función ha sido reemplazada por un valor numérico (10! = 3628800).
De manera similar, para calcular la función log Gamma en un punto:
# include " gcem.hpp "
int main ()
{
constexpr long double x = 1.5 ;
constexpr long double res = gcem::lgamma (x);
return 0 ;
}
Código de montaje:
.LCPI0_0:
.long 1069547520 # float 1 . 5
.LCPI0_1:
.quad - 622431863250842976 # x86_fp80 - 0 . 120782237635245222719
.short 49147
.zero 6
main: # @main
push rbp
mov rbp , rsp
xor eax , eax
mov dword ptr [ rbp - 4 ], 0
fld dword ptr [ rip + .LCPI0_0 ]
fstp tbyte ptr [ rbp - 32 ]
fld tbyte ptr [ rip + .LCPI0_1 ]
fstp tbyte ptr [ rbp - 48 ]
pop rbp
ret