#!/usr/bin/env python # coding: utf-8 # # Please Stop using Pylab # [Edit] thanks to [Randy Olson](https://github.com/Carreau/posts/pull/3) for sending me a PR with grammar and spelling corrections. # TL;DR, Please stop advising people to use the `pylab` flag when using IPython. # It is harmful. If you want to help IPython, try to avoid retweeting, and # promoting things that use the `pylab` flag and make the authors aware of the issues. # # Use explicit import, and `%matplotlib inline` magic. It is better (and supports switching between inline/not inline.) # # # This was mainly prompted by a day where I came across consecutive issues due to # the pylab flag, and people happy to discover it. # # ## Pylab, my worst friend # When IPython 1.0 was released almost 6 months ago, we had quite a few decisions to # make in less than a week and loads of discussions at the last moment. One of # those decisions comes and goes often: we want to get rid of this stupid `pylab` flag. If # you look at our stable (1.0) dev doc and examples there shouldn't be # a mention of the `pylab` flag anywhere. If there is, we will quickly remove it. # Why? Because it is harmful, first to us, then to new users, to the Python # community, and finally to research in general. # Do you know about pylab? If you don't, please be extra careful and try to avoid it as much as possible. # It is like smoking: it looks cool at first, then after a few years you realise you can live without it, # but it makes you sick. # # You think you know what `pylab` does? Really? Take few seconds to think what the `pylab` flag is doing, then read the rest. # ## What is it supposed to do? # The `pylab` **package** main purpose was to build a [transition tool](https://wiki.scipy.org/PyLab) # from other languages to Python. As it was more and more common and painful to do the same import # in IPython every time when only the IPython shell was around, the `--pylab` flag was added. Basically, it did the following: # # ```python # import numpy # import matplotlib # from matplotlib import pylab, mlab, pyplot # np = numpy # plt = pyplot # # from IPython.core.pylabtools import figsize, getfigs # # from pylab import * # from numpy import * # ``` # # Did you get it right the first time without cheating ? Are you able to say what has been imported # in `from pylab import *` ? in `from numpy import *` ? # # # Of course, that is not the only thing it does. But was it your intention to do that the last time you used pylab? # ### It is irreversible # Once you activate pylab mode, there is no going back. You cannot unimport # things. Of course, with the `%pylab` magic you can always restart your kernel, # but with the flag, all your kernels will start in pylab mode. Are you **sure** # you will not need a non-pylab kernel? # ### Unclear # When using the `pylab` flag, your audience usually has no way of knowing that you # used the flag. If I use `plot(range(10))`, what will happen? Will it pop up a # figure ? Inline it? Or throw an error? # # In[ ]: plot(range(10)) # Because I'm mean, I won't execute the cell, so that you don't know whether or # not I'm running in pylab mode or not. You might think it's not a big deal, but # in teaching and research it is important to communicate exactly what you are doing. # ### It pollutes the namespace # In[1]: len(get_ipython().user_ns.keys()) # In[2]: get_ipython().run_line_magic('pylab', '') # IPython 2.0-dev gives some warning, and will tell you wether it clobbers already non-built-in variables in the user namespace. # In[3]: len(get_ipython().user_ns.keys()) # Can you really tell me the 948 additional things you now have in your namespace? Not a big deal? Really? # ### It replaces built-ins # In[6]: sum,all # Both used to be `,` before using pylab, and this **changes the behavior of your programs!** # For example, it leads to non-pickable object in some cases: # # # @treycausey on Twitter # # > @ogrisel @myusuf3 Ah, very curious. It loads fine in IPython but not in an IPython notebook. I must have a namespace collision or something. # # Me: # > Let me guess: `$ipython notebook --pylab`? But `$ipython` alone? # ### Other unrelated actions # IPython developed and added the rich display protocol, so we added `from IPython.display import display` to what `import pylab` does. # # Because matplotlib can work with different event loops, pylab added options to activate qt/gtk/osx/etc. event loops, and with the QtConsole and Notebook creation, the ability to select the inline backend, which registers display hooks. # The main things users remember, and often the main message that you can read here and there is that: # # > You need to use Pylab to get inline figures. # # Which is **false**. Inline pylab mode is a convenient method to activate inline, and set up a display hook with matplotlib. You do not need pylab to have inline images, nor do you need matplotlib. # With 1.0 and above the recommended way to set up inline figures would be to use `%matplotlib`. # # ### Side Effects # The worst part is it has the side effect of making people use `pylab` without even knowing it. Later on, they start asking question about how to reuse a graph in matplotlib because no one ever encounters the following code any more: # # ``` # fig,ax = subplots(1,1) # ax.plot(...) # ``` # # or why their script suddenly does not work in plain Python but works in IPython. # # ### It kills kittens, with a spoon... # Maybe not kittens, but it will force developers to explain the same things, again, and again, and again... # In[8]: from IPython.display import YouTubeVideo YouTubeVideo('9VDvgL58h_Y',start=4*60+27) # ## Make `--pylab` disappear. # Of course, we will not remove the `--pylab` flag for compatibility reasons, but please, for 2014, make the following resolutions: # # - Use `%matplotlib [inline|qt|osx|gtx]` to select the right backend/event hook. # - Use explicit imports # - Make people aware of the issues # - Help by making no new articles/tutorials that mention `--pylab` # # If really you only [have 10 seconds left](https://xkcd.com/1168/), the `%pylab` magic is fine. # As usual, this has been written in an IPython Notebook. You can send me pull request if I made mistakes, or if you have any additional remarks on why you shouldn't use `--pylab`.