41

我似乎无法在任何地方找到答案!我在这里找到了一个讨论,但尝试这个我得到了TypeError: 'NoneType' object is not iterable

>>> import numpy as np
>>> import matplotlib.pyplot as plt
>>> x, y = np.meshgrid(np.arange(10),np.arange(10))
>>> z = x + y
>>> cs = plt.contourf(x,y,z,levels=[2,3])
>>> cs.collections[0].set_label('test')
>>> plt.legend()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/matplotlib/pyplot.py", line 2791, in legend
    ret =  gca().legend(*args, **kwargs)
  File "/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/matplotlib/axes.py", line 4475, in legend
    self.legend_ = mlegend.Legend(self, handles, labels, **kwargs)
  File "/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/matplotlib/legend.py", line 365, in __init__
    self._init_legend_box(handles, labels)
  File "/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/matplotlib/legend.py", line 627, in _init_legend_box
    handlebox)
  File "/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/matplotlib/legend_handler.py", line 110, in __call__
    handlebox.get_transform())
  File "/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/matplotlib/legend_handler.py", line 352, in create_artists
    width, height, fontsize)
  File "/opt/local/Library/Frameworks/Python.framework/Versions/2.7/lib/python2.7/site-packages/matplotlib/legend_handler.py", line 307, in get_sizes
    size_max = max(orig_handle.get_sizes())*legend.markerscale**2
TypeError: 'NoneType' object is not iterable

编辑:我正在寻找这样的东西:

kamland 太阳能三角洲卡方图

4

3 回答 3

55

您也可以直接使用轮廓线来完成,而无需使用代理艺术家。

import matplotlib
import numpy as np
import matplotlib.cm as cm
import matplotlib.mlab as mlab
import matplotlib.pyplot as plt

matplotlib.rcParams['xtick.direction'] = 'out'
matplotlib.rcParams['ytick.direction'] = 'out'

delta = 0.025
x = np.arange(-3.0, 3.0, delta)
y = np.arange(-2.0, 2.0, delta)
X, Y = np.meshgrid(x, y)
Z1 = mlab.bivariate_normal(X, Y, 1.0, 1.0, 0.0, 0.0)
Z2 = mlab.bivariate_normal(X, Y, 1.5, 0.5, 1, 1)
# difference of Gaussians
Z = 10.0 * (Z2 - Z1)



# Create a simple contour plot with labels using default colors.  The
# inline argument to clabel will control whether the labels are draw
# over the line segments of the contour, removing the lines beneath
# the label
plt.figure()
CS = plt.contour(X, Y, Z)
plt.clabel(CS, inline=1, fontsize=10)
plt.title('Simplest default with labels')

labels = ['line1', 'line2','line3','line4',
           'line5', 'line6']
for i in range(len(labels)):
    CS.collections[i].set_label(labels[i])

plt.legend(loc='upper left')

将产生:

图例和标签

但是,您可能还想根据自己的需要查看注释。在我看来,它会给你一个更细粒度的控制你在图像上写的位置和内容,这是带有一些注释的相同示例:

### better with annotation, more flexible
plt.figure(2)
CS = plt.contour(X, Y, Z)
plt.clabel(CS, inline=1, fontsize=10)
plt.title('Simplest default with labels')

plt.annotate('some text here',(1.4,1.6))
plt.annotate('some text there',(-2,-1.5))

带注释的图

于 2012-05-08T07:05:50.977 回答
38

您可以创建代理艺术家来制作图例:

import numpy as np
import matplotlib.pyplot as plt
x, y = np.meshgrid(np.arange(10),np.arange(10))
z = np.sqrt(x**2 + y**2)
cs = plt.contourf(x,y,z,levels=[2,3,4,6])

proxy = [plt.Rectangle((0,0),1,1,fc = pc.get_facecolor()[0]) 
    for pc in cs.collections]

plt.legend(proxy, ["range(2-3)", "range(3-4)", "range(4-6)"])
plt.show()

在此处输入图像描述

于 2012-05-08T01:00:12.520 回答
0

我有一个类似的问题,但需要超出HYRY 的回答。为了使包对用户友好,我想ax.legend()在不需要用户传递任何句柄的情况下工作,这可以通过将标签传递给代理来实现

proxy = plt.Rectangle((0, 0), 1, 1, fc='red', label='some label')

然后将代理添加到轴的补丁中:

ax.patches += [proxy]

ax = plt.gca()获取当前轴)

此答案中对此进行了更详细的描述。

于 2019-07-14T20:16:33.313 回答