Creación de un tamaño de leyenda de dispersión de matplotlib relacionado

Estoy buscando una manera de incluir una leyenda (matplotlib) que describa el tamaño de los puntos en un diagtwig de dispersión, ya que esto podría estar relacionado con otra variable, como en este ejemplo básico:

import numpy as np import matplotlib.pyplot as plt N = 50 x = np.random.rand(N) y = np.random.rand(N) a2 = 400*np.random.rand(N) plt.scatter(x, y, s=a2, alpha=0.5) plt.show() 

(inspirado en: http://matplotlib.org/examples/shapes_and_collections/scatter_demo.html )

de modo que en la leyenda habría idealmente pocos puntos correspondientes a los tamaños 0-400 (la variable a2 ), de acuerdo con s descriptor de s en scatter .

La solución a continuación utiliza pandas para agrupar los tamaños en contenedores establecidos (con groupby ). Traza cada grupo y le asigna una etiqueta y un tamaño para los marcadores. He utilizado la receta binning de esta pregunta .

Tenga en cuenta que esto es ligeramente diferente a su problema establecido, ya que los tamaños de los marcadores están agrupados, esto significa que dos elementos en a2 , digamos 36 y 38, tendrán el mismo tamaño que están dentro de la misma agrupación. Siempre puedes boost el número de contenedores para hacerlo más fino según te convenga.

Con este método, puede variar otros parámetros para cada bandeja, como la forma o el color del marcador.

 import numpy as np import matplotlib.pyplot as plt import pandas as pd N = 50 M = 5 # Number of bins x = np.random.rand(N) y = np.random.rand(N) a2 = 400*np.random.rand(N) # Create the DataFrame from your randomised data and bin it using groupby. df = pd.DataFrame(data=dict(x=x, y=y, a2=a2)) bins = np.linspace(df.a2.min(), df.a2.max(), M) grouped = df.groupby(np.digitize(df.a2, bins)) # Create some sizes and some labels. sizes = [50*(i+1.) for i in range(M)] labels = ['Tiny', 'Small', 'Medium', 'Large', 'Huge'] for i, (name, group) in enumerate(grouped): plt.scatter(group.x, group.y, s=sizes[i], alpha=0.5, label=labels[i]) plt.legend() plt.show() 

Trama

Esto también funcionará, y creo que es un poco más simple:

 msizes = np.array([3, 4, 5, 6, 7, 8]) l1, = plt.plot([],[], 'or', markersize=msizes[0]) l2, = plt.plot([],[], 'or', markersize=msizes[1]) l3, = plt.plot([],[], 'or', markersize=msizes[2]) l4, = plt.plot([],[], 'or', markersize=msizes[3]) labels = ['M3', 'M4', 'M5', 'M6'] leg = plt.legend([l1, l2, l3, l4], labels, ncol=1, frameon=True, fontsize=12, handlelength=2, loc = 8, borderpad = 1.8, handletextpad=1, title='My Title', scatterpoints = 1) 

Tomado de: Leyendas de tamaño de punto en plots de mapa base y matplotlib

Casi me gusta la respuesta de mjp, pero no funciona del todo porque el argumento ‘markersize’ de plt.plot no significa lo mismo que el argumento ‘s’ de plt.scatter. Sus tamaños serán incorrectos usando plt.plot.

En su lugar, utilice:

  marker1 = plt.scatter([],[], s=a2.min()) marker2 = plt.scatter([],[], s=a2.max()) legend_markers = [marker1, marker2] labels = [ str(round(a2.min(),2)), str(round(a2.max(),2)) ] fig.legend(handles=legend_markers, labels=labels, loc='upper_right', scatterpoints=1) 

Sobre la base de las respuestas de mjp y jpobst, si tiene más de dos tamaños discretos, puede crear un bucle e incluir las tags en la llamada a plt.scatter ():

 msizes = [3, 4, 5, 6, 7] markers = [] for size in msizes: markers.append(plt.scatter([],[], s=size, label=size) plt.legend(handles=markers) 

Tenga en cuenta que puede formatear la etiqueta utilizando el formato de cadena estándar, como label = ('M%d' %size) para las tags en la respuesta de mjp.

Encontré esto aquí , es tan fácil y conciso. Espero eso ayude

 import matplotlib.pyplot as plt import numpy as np import plotly.plotly as py import plotly.tools as tls fig = plt.figure() ax = fig.add_subplot(111) x = [0,2,4,6,8,10] y = [0]*len(x) s = [100, 400, 490, 600, 240, 160] # Specifies marker size ax.scatter(x,y,s=s) ax.set_title('Plot with Different Marker size, matplotlib and plotly') plotly_fig = tls.mpl_to_plotly( fig ) plotly_fig['layout']['showlegend'] = True plotly_url = py.plot(plotly_fig, filename='mpl-marker-size')