Matplotlib-etiquetar cada contenedor


Actualmente estoy usando Matplotlib para crear un histograma:

introduzca la descripción de la imagen aquí

import matplotlib
matplotlib.use('Agg')
import matplotlib.pyplot as pyplot
...
fig = pyplot.figure()
ax = fig.add_subplot(1,1,1,)
n, bins, patches = ax.hist(measurements, bins=50, range=(graph_minimum, graph_maximum), histtype='bar')

#ax.set_xticklabels([n], rotation='vertical')

for patch in patches:
    patch.set_facecolor('r')

pyplot.title('Spam and Ham')
pyplot.xlabel('Time (in seconds)')
pyplot.ylabel('Bits of Ham')
pyplot.savefig(output_filename)

Me gustaría hacer las etiquetas del eje x un poco más significativas.

En primer lugar, las marcas del eje x aquí parecen estar limitadas a cinco marcas. No importa lo que haga, parece que no puedo cambiar esto, incluso si agrego más xticklabels, solo usa los primeros cinco. No estoy seguro de cómo Matplotlib calcula esto, pero supongo que se calcula automáticamente a partir del rango/datos?

¿Hay alguna manera de aumentar la resolución de las etiquetas x-tick - ¿incluso hasta el punto de una para cada barra/contenedor?

(Idealmente, también me gustaría que los segundos se reformateen en microsegundos / milisegundos, pero esa es una pregunta para otro día).

En segundo lugar, me gustaría cada barra individual etiquetada - con el número real en ese contenedor, así como el porcentaje del total de todos los contenedores.

La salida final podría ser algo como esto:

introduzca la descripción de la imagen aquí

Es algo así posible con Matplotlib?

Saludos, Victor

Author: victorhooi, 2011-06-15

2 answers

¡Claro! Para establecer las garrapatas, sólo, bueno... Establezca las marcas (ver matplotlib.pyplot.xticks o ax.set_xticks). (Además, no es necesario establecer manualmente el facecolor de los parches. Puedes simplemente pasar un argumento de palabra clave.)

Para el resto, necesitará hacer algunas cosas un poco más elegantes con el etiquetado, pero matplotlib lo hace bastante fácil.

Como ejemplo:

import matplotlib.pyplot as plt
import numpy as np
from matplotlib.ticker import FormatStrFormatter

data = np.random.randn(82)
fig, ax = plt.subplots()
counts, bins, patches = ax.hist(data, facecolor='yellow', edgecolor='gray')

# Set the ticks to be at the edges of the bins.
ax.set_xticks(bins)
# Set the xaxis's tick labels to be formatted with 1 decimal place...
ax.xaxis.set_major_formatter(FormatStrFormatter('%0.1f'))

# Change the colors of bars at the edges...
twentyfifth, seventyfifth = np.percentile(data, [25, 75])
for patch, rightside, leftside in zip(patches, bins[1:], bins[:-1]):
    if rightside < twentyfifth:
        patch.set_facecolor('green')
    elif leftside > seventyfifth:
        patch.set_facecolor('red')

# Label the raw counts and the percentages below the x-axis...
bin_centers = 0.5 * np.diff(bins) + bins[:-1]
for count, x in zip(counts, bin_centers):
    # Label the raw counts
    ax.annotate(str(count), xy=(x, 0), xycoords=('data', 'axes fraction'),
        xytext=(0, -18), textcoords='offset points', va='top', ha='center')

    # Label the percentages
    percent = '%0.0f%%' % (100 * float(count) / counts.sum())
    ax.annotate(percent, xy=(x, 0), xycoords=('data', 'axes fraction'),
        xytext=(0, -32), textcoords='offset points', va='top', ha='center')


# Give ourselves some more room at the bottom of the plot
plt.subplots_adjust(bottom=0.15)
plt.show()

introduzca la descripción de la imagen aquí

 90
Author: Joe Kington,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-06-15 04:35:48

Para agregar prefijos SI a sus etiquetas de eje que desea utilizar QuantiPhy. De hecho, en su documentación tiene un ejemplo que muestra cómo hacer esto exactamente: MatPlotLib Example .

Creo que agregarías algo como esto a tu código:

from matplotlib.ticker import FuncFormatter
from quantiphy import Quantity

time_fmtr = FuncFormatter(lambda v, p: Quantity(v, 's').render(prec=2))
ax.xaxis.set_major_formatter(time_fmtr)
 0
Author: August West,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-07-16 00:46:28