Matplotlib scatterplot con leyenda

Estoy interesado en trazar una leyenda en mi diagtwig de dispersión. Mi código actual se ve así

x=[1,2,3,4] y=[5,6,7,8] classes = [2,4,4,2] plt.scatter(x, y, c=classes, label=classes) plt.legend() 

El problema es que cuando se crea la ttwig, la leyenda se muestra como una matriz en lugar de mostrar las tags únicas y sus clases.

Así se ve la trama.

Soy consciente de que esta es una pregunta discutida anteriormente en temas como este, sin embargo, siento que mi problema es aún más simple y que la solución no encaja. Además, en ese ejemplo, la persona está especificando los colores, sin embargo, en mi caso, sé de antemano cuántos colores necesitaré. Además, en este ejemplo, el usuario está creando varias dispersiones, cada una con un color único. De nuevo, esto no es lo que quiero. Mi objective es simplemente crear el gráfico utilizando una matriz x, y y las tags. es posible?

Gracias.

En realidad, ambas preguntas vinculadas proporcionan una manera de lograr el resultado deseado.

El método más sencillo es crear tantos diagtwigs de dispersión como existan clases únicas y dar a cada uno un único color y una entrada de leyenda.

 import matplotlib.pyplot as plt x=[1,2,3,4] y=[5,6,7,8] classes = [2,4,4,2] unique = list(set(classes)) colors = [plt.cm.jet(float(i)/max(unique)) for i in unique] for i, u in enumerate(unique): xi = [x[j] for j in range(len(x)) if classes[j] == u] yi = [y[j] for j in range(len(x)) if classes[j] == u] plt.scatter(xi, yi, c=colors[i], label=str(u)) plt.legend() plt.show() 

introduzca la descripción de la imagen aquí

En caso de que las clases sean tags de cadena, la solución se vería un poco diferente, ya que necesita obtener los colores de su índice en lugar de usar las propias clases.

 import numpy as np import matplotlib.pyplot as plt x=[1,2,3,4] y=[5,6,7,8] classes = ['X','Y','Z','X'] unique = np.unique(classes) colors = [plt.cm.jet(i/float(len(unique)-1)) for i in range(len(unique))] for i, u in enumerate(unique): xi = [x[j] for j in range(len(x)) if classes[j] == u] yi = [y[j] for j in range(len(x)) if classes[j] == u] plt.scatter(xi, yi, c=colors[i], label=str(u)) plt.legend() plt.show() 

introduzca la descripción de la imagen aquí

Tal vez llenar una table manualmente podría ser útil aquí. Otra idea es usar la colorbar si tus clases son números contiguos. Estoy mostrando ambos enfoques en uno.

 x=[1,2,3,4,5,6,7] y=[1,2,3,4,5,6,7] classes = [2,4,4,2,1,3,5] cmap = cm.get_cmap("viridis",5) plt.scatter(x, y, c=classes, label=classes,cmap=cmap,vmin=0.5,vmax=5.5) plt.colorbar() unique_classes = list(set(classes)) plt.table(cellText=[[x] for x in unique_classes], loc='lower right', colWidths=[0.2],rowColours=cmap(np.array(unique_classes)-1), rowLabels=['label%d'%x for x in unique_classes], colLabels=['classes']) 

introduzca la descripción de la imagen aquí