python - abs(double complex) in Cython -
how absolute value double complex variable?
def f(): cdef double complex aaa = 1 + 2j cdef double bbb = abs(aaa) the second assignment highlighted yellow in cython -a html output: aaa converted python object prior applying abs().
how call abs() on c/cpp level?
ps understand
cdef extern "complex.h": double abs(double complex) would solve it, see following instructions in generated c/cpp file:
#if cython_ccomplex #define __pyx_c_abs_double(z) (::std::abs(z)) #endif and like, supposed choose correct header include (<complex> or "complex.h" or custom code) depending on compilation flags.
how utilize instructions?
more useful contribution:
the following semi-tested addition fix "cython/compiler/builtin.py". should pretty obvious add it:
builtinfunction('abs', none, none, "__pyx_c_abs{0}".format(pyrextypes.c_double_complex_type.funcsuffix), #utility_code = utilitycode.load('arithmetic', 'complex.c', pyrextypes.c_double_complex_type._utility_code_context()), func_type = pyrextypes.cfunctype( pyrextypes.c_double_type, [ pyrextypes.cfunctypearg("arg", pyrextypes.c_double_complex_type, none) ], is_strict_signature = true)), builtinfunction('abs', none, none, "__pyx_c_abs{0}".format(pyrextypes.c_float_complex_type.funcsuffix), #utility_code = utilitycode.load('arithmetic', 'complex.c', pyrextypes.c_float_complex_type._utility_code_context()), func_type = pyrextypes.cfunctype( pyrextypes.c_float_type, [ pyrextypes.cfunctypearg("arg", pyrextypes.c_float_complex_type, none) ], is_strict_signature = true)), builtinfunction('abs', none, none, "__pyx_c_abs{0}".format(pyrextypes.c_longdouble_complex_type.funcsuffix), #utility_code = utilitycode.load('arithmetic', 'complex.c', pyrextypes.c_longdouble_complex_type._utility_code_context()), func_type = pyrextypes.cfunctype( pyrextypes.c_longdouble_type, [ pyrextypes.cfunctypearg("arg", pyrextypes.c_longdouble_complex_type, none) ], is_strict_signature = true)), it appears work. hasn't been run through full cython test-suite. doesn't yet generate correct code @ top of file(but shouldn't need since use complex double does). doesn't yet work in nogil block.
i'll submit cython github once i've looked @ these issues.
original answer:
the whole thing made more complicated since cython attempts use "native" layout complex type. code generated cython:
#if cython_ccomplex #ifdef __cplusplus typedef ::std::complex< double > __pyx_t_double_complex; #else typedef double _complex __pyx_t_double_complex; #endif #else typedef struct { double real, imag; } __pyx_t_double_complex; #endif in cases types should have compatible memory layout (i think), worst case bit of type casting should let use implementation's abs function.
to add confusion, if @ generated cython code (search through various #if cython_ccomplex blocks in generated file) appears cython defines fast versions of abs (and other useful functions) these types, fails use them intelligently, falling python implementation.
if you're going through c need tell cython cabs complex.h:
cdef extern "complex.h": double cabs(double complex) def f(): cdef double complex aaa = 1 + 2j cdef double bbb = cabs(aaa) return bbb if you're going through c++ need tell cython c++ standard library abs. unfortunately it's unable make link between libcpp.complex.complex in predefined wrapper , double complex type, need tell function yourself:
cdef extern "<complex>": double abs(double complex) def f(): cdef complex aaa = 1 + 2j cdef double bbb = abs(aaa) return bbb i don't know if cython_ccomplex isn't defined, think that's you'd have explicitly anyway.
Comments
Post a Comment