web-dev-qa-db-fra.com

Comment créer une barre de couleurs standard pour une série de tracés en python

J'utilise matplotlib pour tracer des données en python et les tracés nécessitent une barre de couleur standard. Les données consistent en une série de matrices NxM contenant des informations sur la fréquence, de sorte qu'un simple tracé imshow () donne un histogramme 2D avec une fréquence décrivant la couleur. Chaque matrice contient des données dans des plages différentes mais se chevauchant. Imshow normalise les données de chaque matrice dans l'intervalle 0-1, ce qui signifie que, par exemple, le tracé de la matrice A sera identique au tracé de la matrice 2 * A (bien que la barre de couleur indique le double des valeurs). Ce que je voudrais, c'est que la couleur rouge, par exemple, corresponde à la même fréquence dans toutes les parcelles. En d'autres termes, une seule barre de couleur suffirait pour toutes les parcelles. Toutes les suggestions seraient grandement appréciées.

37
user1010845

Ne pas voler la réponse de @ ianilis, mais je voulais ajouter un exemple ...

Il existe plusieurs façons, mais la plus simple consiste simplement à spécifier vmin et vmax kwargs à imshow. Vous pouvez également créer une instance matplotlib.cm.Colormap et la spécifier, mais cela est plus compliqué que nécessaire pour les cas simples.

Voici un exemple rapide avec une barre de couleur unique pour toutes les images:

import numpy as np
import matplotlib.pyplot as plt

# Generate some data that where each slice has a different range
# (The overall range is from 0 to 2)
data = np.random.random((4,10,10))
data *= np.array([0.5, 1.0, 1.5, 2.0])[:,None,None]

# Plot each slice as an independent subplot
fig, axes = plt.subplots(nrows=2, ncols=2)
for dat, ax in Zip(data, axes.flat):
    # The vmin and vmax arguments specify the color limits
    im = ax.imshow(dat, vmin=0, vmax=2)

# Make an axis for the colorbar on the right side
cax = fig.add_axes([0.9, 0.1, 0.03, 0.8])
fig.colorbar(im, cax=cax)

plt.show()

enter image description here

72
Joe Kington

La solution la plus simple consiste à appeler clim (lower_limit, upper_limit) avec les mêmes arguments pour chaque tracé.

9
Christian Alis

Ceci ne répond qu'à la moitié de la question, ou plutôt en commence une nouvelle . Si vous changez 

data *= np.array([0.5, 1.0, 1.5, 2.0])[:,None,None]

à

data *= np.array([2.0, 1.0, 1.5, 0.5])[:,None,None]

votre barre de couleur ira de 0 à 0,5 ce qui dans ce cas va du bleu foncé au bleu légèrement plus clair et ne couvrira pas toute la plage (0 à 2) . La barre de couleur ne montrera que les couleurs de la dernière image ou du dernier contour vmin et vmax.

2
robert

Je n'étais pas satisfait des solutions suggérant de définir manuellement les variables vmin et vmax. J'ai donc décidé de lire les limites de chaque tracé et de définir automatiquement les variables vmin et vmax.

L'exemple ci-dessous montre trois graphiques d'échantillons provenant de distributions normales avec une valeur moyenne croissante. 

import matplotlib.pyplot as plt
from mpl_toolkits.axes_grid1 import ImageGrid
import numpy as np

numberOfPlots = 3
data = []
for i in range(numberOfPlots):
    mean = i
    data.append(np.random.normal(mean, size=(100,100)))

fig = plt.figure()
grid = ImageGrid(fig, 111, nrows_ncols=(1,numberOfPlots), cbar_mode='single')
ims = []
for i in range(numberOfPlots):
    ims.append(grid[i].imshow(data[i]))
    grid[i].set_title("Mean = " + str(i))

clims = [im.get_clim() for im in ims]
vmin = min([clim[0] for clim in clims])
vmax = max([clim[1] for clim in clims])
for im in ims:
    im.set_clim(vmin=np.floor(vmin),vmax=np.ceil(vmax))
grid[0].cax.colorbar(ims[0]) # with cbar_mode="single", cax attribute of all axes are identical    

fig.show()

 enter image description here

0
toliveira