Rendering fractals with numpy and numba


Requirements: numpy, matplotlib and numba.

How to render nice fractal images with numpy and numba in one second

Rendering fractals like the Mandelbrot set, the Julia set and the Newton fractal are almost routine exercises for every beginner in python. They are very easy to code, but can produce quite appealing images.

The only headache when rendering fractals with python is efficiency: python is notoriously slow for doing large scale numeric computations, even most people know they should use numpy to accelarate this process, they did not explore the full power of numpy, and only very few people know that their program could be further accelarated by using numba.

In this program I tried to do my best in the following respects:

  1. The code should be as simple as possible.
  2. The code should run as fast as possible.
  3. The result should be as nice as possible.

Of course one cannot expect he could render very artistic fractal images with only a few lines of code, but he can do quite good in all these three respects, this is what I want to show you in this post.

The main tips and tricks are:

  1. Use numpy.ogrid to create your 2D grid in the complex plane.
  2. Use numpy.frompyfunc to convert your "escaping time" function into a vectorized one.
  3. Use numba to specify the data type of the inputs and the outputs. Just add an one-line decorator!
  4. Do not use the putpixel() function in PIL to iterate over the pixels, fromarray is a better choice.
  5. Explictly write z.real*z.real+z.imag*z.imag instead of using the abs() function.
  6. z*z is a bit faster than z**2 and z*z*z is a bit faster than z**3.
  7. Finally choose a nice coloring scheme for your image.

To summary, the most import thing you should keep in mind is that

1. Always use vectorized operations instead of the for loop to iterate over the 2D array and render the image. This is because in vectorized operations the CPU can read and send a bunk of data at a time instead of one data at a time.

2. A suitable, simple numba decorator could improve the efficiency a lot.