From 9dedc0f2c3bd201f32daed00e4c9e88df6050468 Mon Sep 17 00:00:00 2001 From: Thomas A Caswell Date: Mon, 30 Jun 2014 00:08:50 -0400 Subject: [PATCH 1/3] DOC : change how OO/pyplot/pylab is addressed I assume this will be controversial Addresses #3115 --- doc/faq/usage_faq.rst | 127 ++++++++++++++++++++++++++++-------------- 1 file changed, 86 insertions(+), 41 deletions(-) diff --git a/doc/faq/usage_faq.rst b/doc/faq/usage_faq.rst index 749151f9f3a9..47039121760c 100644 --- a/doc/faq/usage_faq.rst +++ b/doc/faq/usage_faq.rst @@ -55,31 +55,50 @@ Matplotlib is the whole package; :mod:`pylab` is a module in matplotlib that gets installed alongside :mod:`matplotlib`; and :mod:`matplotlib.pyplot` is a module in matplotlib. -Pyplot provides the state-machine interface to the underlying plotting +Pyplot provides the state-machine interface to the underlying OO plotting library in matplotlib. This means that figures and axes are implicitly and automatically created to achieve the desired plot. For example, calling ``plot`` from pyplot will automatically create the necessary figure and axes to achieve the desired plot. Setting a title will then automatically set that title to the current axes object:: - import matplotlib.pyplot as plt - plt.plot(range(10), range(10)) - plt.title("Simple Plot") - plt.show() + .. sourcecode:: ipython + + In [20]: %matplotlib + Using matplotlib backend: Qt4Agg + + In [15]: import matplotlib.pyplot as plt + + In [16]: plt.plot(range(10), range(10)) + Out[16]: [] + + In [17]: plt.title("Simple Plot") + Out[17]: + +This is very convenient for interactive use, however +because the commands have side-effects (altering the global state) +using many :mod:`matplotlib.pyplot` commands in scripts or functions +can lead to unexpected and difficult to track down bugs. -Pylab combines the pyplot functionality (for plotting) with the numpy -functionality (for mathematics and for working with arrays) -in a single namespace, making that namespace -(or environment) even more MATLAB-like. -For example, one can call the `sin` and `cos` functions just like -you could in MATLAB, as well as having all the features of pyplot. +Pylab is a convenience module that imports pyplot (for +plotting) and numpy functionality (for mathematics and for +working with arrays) in a single namespace. You can than bulk import +from pylab:: -The pyplot interface is generally preferred for non-interactive plotting -(i.e., scripting). The pylab interface is convenient for interactive -calculations and plotting, as it minimizes typing. Note that this is -what you get if you use the *ipython* shell with the *-pylab* option, -which imports everything from pylab and makes plotting fully interactive. + .. sourcecode:: ipython + + In [1]: from pylab import * + +to get an even more MATLAB-like environment. For example, one can +call the `sin` and `cos` functions just like you could in MATLAB, as +well as having all the features of pyplot. The pylab interface is +convenient for interactive calculations and plotting, as it minimizes +typing. This is not recommended to use pylab in scripts for the same reasons +bulk importing is discouraged in general. + +For non-interactive use it is suggested to use pyplot to create the +figures and then the OO interface for plotting. .. _coding_styles: @@ -106,18 +125,7 @@ scripts will typically be:: import numpy as np Then one calls, for example, np.arange, np.zeros, np.pi, plt.figure, -plt.plot, plt.show, etc. So, a simple example in this style would be:: - - import matplotlib.pyplot as plt - import numpy as np - x = np.arange(0, 10, 0.2) - y = np.sin(x) - plt.plot(x, y) - plt.show() - -Note that this example used pyplot's state-machine to -automatically and implicitly create a figure and an axes. For full -control of your plots and more advanced usage, use the pyplot interface +plt.plot, plt.show, etc. Use the pyplot interface for creating figures, and then use the object methods for the rest:: import matplotlib.pyplot as plt @@ -129,22 +137,59 @@ for creating figures, and then use the object methods for the rest:: ax.plot(x, y) plt.show() -Next, the same example using a pure MATLAB-style:: +So, why all the extra typing instead of the MATLAB-style (which relies +on global state and a flat namespace)? For very simple things like +this example, the only advantage is academic: the wordier styles are +more explicit, more clear as to where things come from and what is +going on. For more complicated applications, this explicitness and +clarity becomes increasingly valuable, and the richer and more +complete object-oriented interface will likely make the program easier +to write and maintain. + +Typically one finds them selves making the same plots over and over +again, but with different data sets, which leads to needing to write +specialized functions to do the plotting. The recommended function +signature is something like: :: + + def my_plotter(ax, data1, data2, param_dict): + """ + A helper function to make a graph + + Parameters + ---------- + ax : Axes + The axes to draw to + + data1 : array + The x data + + data2 : array + The y data + + param_dict : dict + Dictionary of kwargs to pass to ax.plot + + Returns + ------- + out : list + list of artists added + """ + out = ax.plot(data1, data2, **param_dict) + return out + +which you would then use as:: + + fig, ax = plt.subplots(1, 1) + my_plotter(ax, data1, data2, {'marker':'x'}) - from pylab import * - x = arange(0, 10, 0.2) - y = sin(x) - plot(x, y) - show() +or if you wanted to have 2 sub-plots:: + fig, (ax1, ax2) = plt.subplots(1, 2) + my_plotter(ax1, data1, data2, {'marker':'x'}) + my_plotter(ax2, data3, data4, {'marker':'o'}) -So, why all the extra typing as one moves away from the pure -MATLAB-style? For very simple things like this example, the only -advantage is academic: the wordier styles are more explicit, more -clear as to where things come from and what is going on. For more -complicated applications, this explicitness and clarity becomes -increasingly valuable, and the richer and more complete object-oriented -interface will likely make the program easier to write and maintain. +Again, for these simple examples this style seems like overkill, however +once the graphs get slightly more complex it pays off. .. _what-is-a-backend: From a2b946145b5e9845d05e079d71f6ad6cc4359c6d Mon Sep 17 00:00:00 2001 From: Thomas A Caswell Date: Thu, 3 Jul 2014 22:40:23 -0400 Subject: [PATCH 2/3] DOC : grammer fixes and doc edits - removed from pylab import * - changed some wording --- doc/faq/usage_faq.rst | 32 +++++++++++++------------------- 1 file changed, 13 insertions(+), 19 deletions(-) diff --git a/doc/faq/usage_faq.rst b/doc/faq/usage_faq.rst index 47039121760c..b7699281b84e 100644 --- a/doc/faq/usage_faq.rst +++ b/doc/faq/usage_faq.rst @@ -65,7 +65,7 @@ then automatically set that title to the current axes object:: .. sourcecode:: ipython - In [20]: %matplotlib + In [14]: %matplotlib Using matplotlib backend: Qt4Agg In [15]: import matplotlib.pyplot as plt @@ -81,24 +81,18 @@ because the commands have side-effects (altering the global state) using many :mod:`matplotlib.pyplot` commands in scripts or functions can lead to unexpected and difficult to track down bugs. -Pylab is a convenience module that imports pyplot (for -plotting) and numpy functionality (for mathematics and for -working with arrays) in a single namespace. You can than bulk import -from pylab:: +Pylab is a convenience module that imports pyplot (for plotting) and +numpy functionality (for mathematics and for working with arrays) in a +single namespace. You can than bulk import from pylab to get an even +more MATLAB-like environment. This seems convenient for interactive +calculations and plotting, as it (barely) minimizes typing, however it +is not recommended as it clobbers your namespace. As with :mod:`pyplot`, +it is not recommended to use :mod:`pylab` in scripts and bulk importing +:mod:`pylab` in scripts is discouraged as with all bulk importing. - .. sourcecode:: ipython - - In [1]: from pylab import * - -to get an even more MATLAB-like environment. For example, one can -call the `sin` and `cos` functions just like you could in MATLAB, as -well as having all the features of pyplot. The pylab interface is -convenient for interactive calculations and plotting, as it minimizes -typing. This is not recommended to use pylab in scripts for the same reasons -bulk importing is discouraged in general. - -For non-interactive use it is suggested to use pyplot to create the -figures and then the OO interface for plotting. +For non-interactive plotting it is suggested +to use pyplot to create the figures and then the OO interface for +plotting. .. _coding_styles: @@ -146,7 +140,7 @@ clarity becomes increasingly valuable, and the richer and more complete object-oriented interface will likely make the program easier to write and maintain. -Typically one finds them selves making the same plots over and over +Typically one finds oneself making the same plots over and over again, but with different data sets, which leads to needing to write specialized functions to do the plotting. The recommended function signature is something like: :: From adc9ec4df4412c414fb23f600e414c13110ddb58 Mon Sep 17 00:00:00 2001 From: Thomas A Caswell Date: Sat, 12 Jul 2014 23:39:14 -0400 Subject: [PATCH 3/3] DOC : edits to usage_faq.rst --- doc/faq/usage_faq.rst | 63 ++++++++++++++++++++++--------------------- 1 file changed, 32 insertions(+), 31 deletions(-) diff --git a/doc/faq/usage_faq.rst b/doc/faq/usage_faq.rst index b7699281b84e..731c4c6d2d8e 100644 --- a/doc/faq/usage_faq.rst +++ b/doc/faq/usage_faq.rst @@ -48,47 +48,48 @@ completely, leaving a purely object-oriented approach. .. _pylab: -Matplotlib, pylab, and pyplot: how are they related? +Matplotlib, pyplot and pylab: how are they related? ==================================================== -Matplotlib is the whole package; :mod:`pylab` is a module in matplotlib -that gets installed alongside :mod:`matplotlib`; and :mod:`matplotlib.pyplot` -is a module in matplotlib. +Matplotlib is the whole package; :mod:`matplotlib.pyplot` +is a module in matplotlib; and :mod:`pylab` is a module +that gets installed alongside :mod:`matplotlib`. -Pyplot provides the state-machine interface to the underlying OO plotting -library in matplotlib. This means that figures and axes are implicitly -and automatically created to achieve the desired plot. For example, -calling ``plot`` from pyplot will automatically create the necessary -figure and axes to achieve the desired plot. Setting a title will -then automatically set that title to the current axes object:: +Pyplot provides the state-machine interface to the underlying +object-oriented plotting library. The state-machine implicitly and +automatically creates figures and axes to achieve the desired +plot. For example:: - .. sourcecode:: ipython + import matplotlib.pyplot as plt + import numpy as np - In [14]: %matplotlib - Using matplotlib backend: Qt4Agg + x = np.linspace(0, 2, 100) - In [15]: import matplotlib.pyplot as plt + plt.plot(x, x, label='linear') + plt.plot(x, x**2, label='quadratic') + plt.plot(x, x**3, label='cubic') - In [16]: plt.plot(range(10), range(10)) - Out[16]: [] + plt.xlabel('x label') + plt.ylabel('y label') - In [17]: plt.title("Simple Plot") - Out[17]: + plt.title("Simple Plot") -This is very convenient for interactive use, however -because the commands have side-effects (altering the global state) -using many :mod:`matplotlib.pyplot` commands in scripts or functions -can lead to unexpected and difficult to track down bugs. + plt.legend() -Pylab is a convenience module that imports pyplot (for plotting) and -numpy functionality (for mathematics and for working with arrays) in a -single namespace. You can than bulk import from pylab to get an even -more MATLAB-like environment. This seems convenient for interactive -calculations and plotting, as it (barely) minimizes typing, however it -is not recommended as it clobbers your namespace. As with :mod:`pyplot`, -it is not recommended to use :mod:`pylab` in scripts and bulk importing -:mod:`pylab` in scripts is discouraged as with all bulk importing. + plt.show() + +The first call to ``plt.plot`` will automatically create the necessary +figure and axes to achieve the desired plot. Subsequent calls to +``plt.plot`` re-use the current axes and each add another line. +Setting the title, legend, and axis labels also automatically use the +current axes and set the title, create the legend, and label the axis +respectively. + +:mod:`pylab` is a convenience module that bulk imports +:mod:`matplotlib.pyplot` (for plotting) and :mod:`numpy` +(for mathematics and working with arrays) in a single name space. +Although many examples use :mod:`pylab`, it is no longer recommended. For non-interactive plotting it is suggested to use pyplot to create the figures and then the OO interface for @@ -112,7 +113,7 @@ The only caveat is to avoid mixing the coding styles for your own code. Of the different styles, there are two that are officially supported. Therefore, these are the preferred ways to use matplotlib. -For the preferred pyplot style, the imports at the top of your +For the pyplot style, the imports at the top of your scripts will typically be:: import matplotlib.pyplot as plt