## CYTHON-GSL

Python extension modules can be written in Cython a compiled language rather similar to Python itself, and capable to be significantly faster than standard Python code. Moreover, existing C and C++ libraries can be easily interfaced within a Cython module as shown in this note.

CythonGSL, for instance, provides a Cython interface for the GNU Scientific Library (GSL). The GSL can be installed on Windows from the MINGW64 package manager as follows:

` $ pacman -S mingw-w64-x86_64-gsl `

On Windows, I prefer to use a Python instance that supports the MSVC compiler, as described in one of my previous notes, where I have installed CythonGSL with PIP.

` $ pip install cythongsl`

## Find the roots of a second order polynomial

A root (solution) of a quadratic equation is the value of *x* for which the second order univariate polynomial *a x²+b x + c* is equal to zero, *a,b,c* are termed the coefficients.

A graphical representation will make it easier to understand this simple problem. Let's take for example the following quadratic equation *2x² + 4 x - 4 = 0*, which has two non-trivial real solutions x≅2.7 and x≅0.8, the two points where our parabola intersects the x-axis (see the graph below).

### Cython module

The following Cython code allows calling the external GSL function ** gsl_poly_complex_solve_quadratic** from a Python module.

```
# filename: quadratic.pyx
from cython_gsl cimport *
cdef double a
cdef double b
cdef double c
def c_quadratic(a,b,c):
cdef gsl_complex z0
cdef gsl_complex z1
cdef int n
n = gsl_poly_complex_solve_quadratic(a, b, c, &z0, &z1)
print '\n roots %d' % n
print "\nz0 = %f + %f*i" % (GSL_REAL(z0),GSL_IMAG(z0))
print "\nz1 = %f + %f*i" % (GSL_REAL(z1),GSL_IMAG(z1))
```

The C-compiler and the GSL libraries belong to a different set of instances, in order to allow the C-compiler linking the required static libraries I have moved MINGW64 *gsl.a* and *gslcblas.a* files into a new directory and renamed them as *gsl.lib* and *gslcblas.lib*.

In the *setup.py*, I specified the paths for the MINGW64's header files and the previous two .lib files.

```
# filename:setup.py
from distutils.core import setup
from Cython.Distutils import Extension
from Cython.Distutils import build_ext
import cython_gsl
setup(
include_dirs = [
cython_gsl.get_include(),
"C:\\...\\mingw64\\include"
],
cmdclass = {'build_ext': build_ext},
ext_modules = [Extension("quadratic",
["quadratic.pyx"],
libraries=cython_gsl.get_libraries(),
library_dirs=[cython_gsl.get_library_dir(),
"C:\\...\\cython_gsl\\lib"],
include_dirs=[cython_gsl.get_cython_include_dir()])]
)
```

Now, I can compile this Cython module with:

` $ python setup.py build`

To import the new module in a Python REPL, I just need the following script:

```
# filename: libpath.py
import sys
sys.path.append('./build/lib.win-amd64-3.9')
import quadratic
```