Hi matplotlib developers, I was answering a question on the -users list and came across a gridspec __getitem__ bug which causes an infinite loop if the user tries to iterate over it, because getitem never did a sanity-check when given an integer key.
from matplotlib import gridspec
gs = gridspec.GridSpec(1,2)
gs[100] # no error is given, a SubplotSpec is returned
[x for x in gs] # causes infinite loop before applying patch
# after applying the patch - which is just lines 171-172 in the
# traceback below
In [9]: gs[100]
----------------------------------------------------------
IndexError Traceback (most recent call last)
./matplotlib/<ipython console> in <module>()
./matplotlib/gridspec.pyc
in __getitem__(self, key)
170 key += total
171 if key >= total or key < 0:
--> 172 raise IndexError("index out of range")
173 num1, num2 = key, None
174
IndexError: index out of range
In [10]: [x for x in gs]
Out[10]:
[<matplotlib.gridspec.SubplotSpec object at 0x9b7edcc>,
<matplotlib.gridspec.SubplotSpec object at 0x9b8834c>]
I'm also including a patch for the gridspec docs which create a
grid-of-grids using gridspec in a colorful manner. Note that
there, I explicitly create indexes in the right range, like so:
outer_grid = GridSpec(4, 4)
for i in xrange(16):
inner_grid = GridSpecFromSubplotSpec(3, 3, subplot_spec=outer_grid[i])
for j in xrange(9):
ax = plt.Subplot(f, inner_grid[j])
...
because before applying the getitem patch described above, one
*can't* currently iterate over the spec itself like this:
outer_grid = GridSpec(4, 4)
for cell in outer_grid:
inner_grid = GridSpecFromSubplotSpec(3, 3, subplot_spec=cell)
for subcell in inner_grid:
ax = plt.Subplot(f, subcell)
...
The doc patch also fixes the currently broken .. _gridspec-guide:
anchor name which can be seen peeking out at the top of:
http://matplotlib.sourceforge.net/users/gridspec.html
because there was previously a misplaced leading \ on line 1 of
doc/users/gridspec.rst
best,
--
Paul Ivanov
314 address only used for lists, off-list direct email at:
http://pirsquared.org | GPG/PGP key id: 0x0F3E28F7
Index: doc/users/plotting/examples/demo_gridspec06.py =================================================================== --- doc/users/plotting/examples/demo_gridspec06.py (revision 0) +++ doc/users/plotting/examples/demo_gridspec06.py (revision 0) @@ -0,0 +1,41 @@ +import matplotlib.pyplot as plt +import matplotlib.gridspec as gridspec +import numpy as np +from itertools import product + +def squiggle_xy(a, b, c, d, i=np.arange(0.0, 2*np.pi, 0.05)): + return np.sin(i*a)*np.cos(i*b), np.sin(i*c)*np.cos(i*d) + +f = plt.figure(figsize=(8, 8)) + +# gridspec inside gridspec +outer_grid = gridspec.GridSpec(4, 4, wspace=0.0, hspace=0.0) + +for i in xrange(16): + inner_grid = gridspec.GridSpecFromSubplotSpec(3, 3, + subplot_spec=outer_grid[i], wspace=0.0, hspace=0.0) + a, b = int(i/4)+1,i%4+1 + for j, (c, d) in enumerate(product(range(1, 4), repeat=2)): + ax = plt.Subplot(f, inner_grid[j]) + ax.plot(*squiggle_xy(a, b, c, d)) + ax.set_xticks([]) + ax.set_yticks([]) + f.add_subplot(ax) + +all_axes = f.get_axes() + +#show only the outside spines +for ax in all_axes: + for sp in ax.spines.values(): + sp.set_visible(False) + if ax.is_first_row(): + ax.spines['top'].set_visible(True) + if ax.is_last_row(): + ax.spines['bottom'].set_visible(True) + if ax.is_first_col(): + ax.spines['left'].set_visible(True) + if ax.is_last_col(): + ax.spines['right'].set_visible(True) + +plt.show() + Index: doc/users/gridspec.rst =================================================================== --- doc/users/gridspec.rst (revision 8885) +++ doc/users/gridspec.rst (working copy) @@ -1,4 +1,4 @@ -\.. _gridspec-guide: +.. _gridspec-guide: ************************************************ @@ -129,6 +129,16 @@ .. plot:: users/plotting/examples/demo_gridspec04.py +A Complex Nested GridSpec using SubplotSpec +=========================================== + +Here's a more sophisticated example of nested gridspec where we put +a box around each cell of the outer 4x4 grid, by hiding appropriate +spines in each of the inner 3x3 grids. :: + +.. plot:: users/plotting/examples/demo_gridspec06.py + + GridSpec with Varying Cell Sizes ================================
Index: lib/matplotlib/gridspec.py
===================================================================
--- lib/matplotlib/gridspec.py (revision 8885)
+++ lib/matplotlib/gridspec.py (working copy)
@@ -167,6 +167,8 @@
else:
if key < 0:
key += total
+ if key >= total or key < 0:
+ raise IndexError("index out of range")
num1, num2 = key, None
signature.asc
Description: Digital signature
------------------------------------------------------------------------------ Learn how Oracle Real Application Clusters (RAC) One Node allows customers to consolidate database storage, standardize their database environment, and, should the need arise, upgrade to a full multi-node Oracle RAC database without downtime or disruption http://p.sf.net/sfu/oracle-sfdevnl
_______________________________________________ Matplotlib-devel mailing list [email protected] https://lists.sourceforge.net/lists/listinfo/matplotlib-devel
