# Python for Scientific Computing

## Summary


Fortran has been the language of choice for many decades for scientific computing because of speed. In the 1980s, when a programmer's time was becoming more valuable than compute time, there was a need for languages that were easier to learn and use. For the purpose of research, code-compile-execute workflow gave way to interact-explore-visualize workflow. In this context were born MATLAB, IDL, Mathematica and Maple. 

Modern scientific computing is not just about numerical computing. It needs to be versatile: deal with large datasets, offer richer data structures than just numerical arrays, make network calls, interface with databases, interwork with web apps, handle data in various formats, enable team collaboration, enable easy documentation. 

Python offers all of the above. It's been said that, 

> Python provides a balance of clarity and flexibility without sacrificing performance.

## Discussion

### What makes Python a suitable language for scientific computing?

Python is not just suited for manipulating numbers. It offers a "computational ecosystem" that can fulfil the needs of a modern scientist. Python does well in system integration, in gluing together many different parts contributed by different folks. Python's duck typing is one of the reasons why this is possible. In terms of data types, `memoryview`, `PyCapsule` and NumPy's `array` aid scientific work. 

Python is easy to learn and use. It offers a natural syntax. This enables researchers to express and explore their ideas more directly rather than fight with low-level language syntax. 

With Python, performance bottlenecks can be optimized at a low-level without sacrificing high-level usability. A researcher needs to explore and visualize ideas in an incremental manner. Python allows for this via IPython/Jupyter notebooks and matplotlib. A variety of Python tools can work together and share data within the same runtime environment without having to exchange data only via the filesystem. 


### I'm used to MATLAB. Why should I use Python?

MATLAB is proprietary, expensive and hard to extend. Python is open, community-driven, portable, powerful and extensible. Python is also better with strings, namespaces, classes and GUIs. While MATLAB, along with Simulink, has vast libraries, Python is catching up as many scientific projects are adopting Python. MATLAB is said to be poor at scalability, complex data structures, memory handling, system tasks and database programming. 

However, there are some criticisms of Python (December 2013). Syntax is not consistent since different packages are written by different folks with different needs. There are two ordinary differential equation (ODE) solvers in scipy with incompatible syntax. Duplicated functionality across packages may result in confusion. MATLAB does better with data regression, boundary value problems and partial differential equations (PDE). 

In 2014, Konrad Hinsen commented that Python may not be suitable for small-scale projects where code is written once and rarely maintained thereafter. This becomes a problem when Python scientific libraries are upgraded by deprecating older classes/functions/methods. 


### Should I worry about performance when using Python for scientific research?

The short answer is no. There are many initiatives that aim to make Python faster. PyPy and Pyston do just-in-time (JIT) compilation for better performance. Nuitka aims to replace the Python runtime to automatically transpile code to languages that run fast natively. Numba speeds up math-heavy Python code to native machine instructions with just a few annotations on your Python code. 

While pure Python code is definitely slower when compared to Fortran or C, scientific packages in Python often make use of low-level implementations that are themselves written in Fortran, C, etc. For example, NumPy operations often call BLAS or LAPACK functions that are written in Fortran. 

f2py is enabling Python to directly use Fortran implementations. SWIG and Cython allow us to make calls to optimized C/C++ implementations from within Python. For example, Cython is being used by scikit-learn. Intel Math Kernel Library (MKL) and PyCUDA are also bringing Python on par with Fortran on specific hardware platforms. 


### What are the essential packages for scientific computing in Python?

Here are some packages that could be considered essential:  

    + **numpy**: Multi-dimensional arrays and operations on them. Executes faster than Python.
    + **scipy**: Linear algebra, interpolation, integration, FFT...
    + **matplotlib**: Plotting and data visualization with an API similar to MATLAB. Eases transition from MATLAB to Python.
    + **spyder**: An IDE that includes IPython (for interactive computing).
    + **pandas**: Numerical data structures, data manipulation and analysis.
    + **jupyter**: Web-based sharing of code, graphs, annotations and results.Most Python scientific packages are based on numpy and scipy. If visualization is involved, matplotlib may be used. For higher-level data structures, pandas may be used. Spyder, IPython and Jupyter are simply useful tools for the scientist or engineer.


### Could you name some useful scientific projects/packages in Python?

Here are some that can be applied to any domain:

    + **Image processing**: Pillow, OpenCV, scikit-learn , Mahotas
    + **Visualization**: matplotlib, bokeh, plotly, mayavi, seaborn , basemap, NetworkX
    + **Markov chains**: Markov, MarkovNetwork, PyMarkov, pyEMMA, hmmus
    + **Stochastic process**: stochastic, StochPy, sdeint
    + **Solving PDEs**: FEniCS, SfePy
    + **Convex Optimization**: CVXPY
    + **Units and conversions**: quantities, pint
    + **Multi-precision math**: mpmath, GmPy
    + **Spatial analysis**: cartopy, georasters, PySAL, geopy
    + **Data access**: pydap, cubes, Blaze, bottleneck, pytables
    + **Machine learning**: scikit-learn, Mlpy, TensorFlow, Theano, Caffe, Keras
    + **Natural Language Processing**: NLTK, TextBlob, spaCy, gensim, pycorenlp
    + **Statistics**: statistics, statsmodels, patsy
    + **Tomography**: TomoPy
    + **Symbolic computing**: sympy
    + **Simulations**: SimPy, BlockCanvas, railgun

### Could you name some domain-specific scientific projects/packages in Python?

Since there are dozens of packages for all types of scientific work, we can only give a sample:  

    + **Solar data analysis**: SunPy
    + **Astronomy**: astropy
    + **Chemistry**: thermo, chemlab
    + **Biology**: biopython
    + **Neurosciences**: PsychoPy, NIPY
    + **Life sciences**: DEAP
    + **Network analysis**: NetworkX
    + **Quantum dynamics**: QuTiP
    + **Protein analysis**: ProDy
    + **Neuron simulations**: NEURON
    + **Seismology**: ObsPy
    + **Phylogenetic computing**: DendroPy
    + **Software defined radio**: GNU Radio

### What's the recommended Python distribution for scientific computing?

Installation of Python for scientific work used to be a pain earlier but with modern distributions, this is no longer an issue. 

Rather than install Python's standard distribution and then install scientific packages one by one, the recommended approach is to use an alternative distribution customized for scientific computing: Enthought Canopy, Anaconda, Python(x,y) or WinPython. Enthought Canopy is commercial but the rest are free. Enthought Canopy claims to include 450+ tested scientific and analytic packages. 

Anaconda distribution uses *conda* for package management. The use of virtual environments is recommended so that different projects can use their own specific environments. Powered by Anaconda, Intel offers its own distribution that's optimized for performance. 

SageMath is another distribution that offers a web-based interface and uses Jupyter notebooks. It aims to be the free open source alternative to Magma, Maple, Mathematica and Matlab.


### As a beginner in scientific Python, what should be my learning path?

From tools and environment perspectives, get familiar with using IPython, Jupyter Notebook and optionally Spyder.

After learning the basics of Python, the next step is to learn numpy since it's the base for many scientific packages. With numpy, you can work with matrices and do vectorized operations without having to write explicit loops. You should learn about operations such as reshaping, transposing, filling, copying, concatenating, flattening, broadcasting, filtering and sorting. 

You could then learn scipy to do optimization, linear algebra, integration, and so on. For visualization, matplotlib can be a starting point. For dealing with higher-level data structures and manipulation, learn pandas.

If you wish get into data science, scikit-learn and Theano can be starting points. For statistical modelling, you can learn statsmodels. 


### What useful developer resources are available for scientific computing in Python?

One good place to start learning is the SciPy Lecture Notes.

SciPy Conference is an annual event for Python's scientific community. It also happens in Europe as EuroSciPy and in India as SciPy India. 

EarthPy is a collection of IPython notebooks for learning how to apply Python to Earth sciences.

The Hacker Within, Software Carpentry and Data Carpentry are some communities that bring together research and scientific folks. Although these are not exclusive to Python, Python programmers will find them useful.

## Milestones

1995

*Numeric* is released to enable numerical computations. This is the ancestor of today's *NumPy*. 

2001

Many scientific modules are brought together and released as a single package named *SciPy*. The same year, IPython is born. 

2002

"Python for Scientific Computing Workshop" is organized at Caltech. In 2004, this is renamed as *SciPy Conference* and is now an annual event. In 2008, EuroSciPy is held for the first time. In 2009, 1st SciPy India is held. 

2005

NumPy is released based on an older library named *Numeric*. It also combines features of another library named *Numarray*. NumPy is initially named *SciPy Core* but renamed to *NumPy* in January 2006. 

Jul  
2017

*Anaconda Accelerate* is split into *Intel Distribution for Python* and open source Numba's sub-projects pyculib, pyculib\_sorting and data\_profiler.