Je veux tracer un histogramme 1D simple où les barres doivent suivre le code couleur d'une carte de couleurs donnée.
Voici une MWE
:
import numpy as n
import matplotlib.pyplot as plt
# Random gaussian data.
Ntotal = 1000
data = 0.05 * n.random.randn(Ntotal) + 0.5
# This is the colormap I'd like to use.
cm = plt.cm.get_cmap('RdYlBu_r')
# Plot histogram.
n, bins, patches = plt.hist(data, 25, normed=1, color='green')
plt.show()
qui produit ceci:
Au lieu que la couleur soit green
pour tout l'histogramme, j'aimerais que les colonnes suivent un code de couleur donné par la palette de couleurs définie dans cm
et les valeurs de bins
. Cela signifierait que les bacs proches de zéro ( non de hauteur mais en position) devraient sembler plus bleus et ceux proches d'un plus rouge, selon la palette de couleurs choisie RdYlBu_r
.
Puisque plt.histo
ne prend pas un argument cmap
, je ne sais pas comment lui dire d’utiliser la palette de couleurs définie dans cm
.
La commande hist
renvoie une liste de correctifs. Vous pouvez donc les parcourir et définir leur couleur comme suit:
import numpy as n
import matplotlib.pyplot as plt
# Random gaussian data.
Ntotal = 1000
data = 0.05 * n.random.randn(Ntotal) + 0.5
# This is the colormap I'd like to use.
cm = plt.cm.get_cmap('RdYlBu_r')
# Plot histogram.
n, bins, patches = plt.hist(data, 25, normed=1, color='green')
bin_centers = 0.5 * (bins[:-1] + bins[1:])
# scale values to interval [0,1]
col = bin_centers - min(bin_centers)
col /= max(col)
for c, p in Zip(col, patches):
plt.setp(p, 'facecolor', cm(c))
plt.show()
Pour obtenir les couleurs, vous devez appeler la palette de couleurs avec une valeur comprise entre 0 et 1 . Chiffre obtenu:
Une autre approche consiste à utiliser plt.bar
qui prend une liste de couleurs. Pour déterminer les largeurs et les hauteurs, vous pouvez utiliser numpy.histogram
. Votre palette de couleurs peut être utilisée en recherchant la plage des valeurs x et en les mettant à l'échelle de 0 à 1.
import numpy as n
import matplotlib.pyplot as plt
# Random gaussian data.
Ntotal = 1000
data = 0.05 * n.random.randn(Ntotal) + 0.5
# This is the colormap I'd like to use.
cm = plt.cm.get_cmap('RdYlBu_r')
# Get the histogramp
Y,X = n.histogram(data, 25, normed=1)
x_span = X.max()-X.min()
C = [cm(((x-X.min())/x_span)) for x in X]
plt.bar(X[:-1],Y,color=C,width=X[1]-X[0])
plt.show()
Bien que ce ne soit pas ce que vous avez demandé, si quelqu'un d'autre (comme je l'ai fait) est tombé par hasard à la recherche du moyen de faire la coloration par hauteur des bacs au lieu de l'ordre, le code suivant basé sur la réponse de Bas fonctionnerait:
import numpy as np
import matplotlib.pyplot as plt
Ntotal = 1000
data = 0.05 * np.random.randn(Ntotal) + 0.5
cm = plt.cm.get_cmap('RdYlBu_r')
n, bins, patches = plt.hist(data, 25, normed=1, color='green')
# To normalize your values
col = (n-n.min())/(n.max()-n.min())
for c, p in Zip(col, patches):
plt.setp(p, 'facecolor', cm(c))
plt.show()
J'aime la réponse de Bas Swinckels, mais étant donné que la palette de couleurs cm prend en paramètre une valeur comprise entre 0 et 1, un algorithme plus simple serait comme ceci
import matplotlib.pyplot as plt
Ntotal = 1000
data = 0.05 * n.random.randn(Ntotal) + 0.5
cm = plt.cm.RdBu_r
n, bins, patches = plt.hist(data, 25, normed=1, color='green')
for i, p in enumerate(patches):
plt.setp(p, 'facecolor', cm(i/25)) # notice the i/25
plt.show()