matplotlib - Agregar un segundo eje y relacionado con el primer eje y
(1)
Espero que alguno de ustedes pueda ayudar.
Tengo un gráfico con un valor del eje y y un eje x correspondiente a estos valores y.
Quiero agregar un segundo eje y en el lado derecho de la gráfica.
Los valores que aparecerán en el segundo eje y se determinan a través de los primeros valores del eje y mediante alguna relación: por ejemplo, y2 podría ser
y2 = y1**2 - 100
.
¿Cómo hago un segundo eje y que tenga sus valores determinados por los valores y1, de modo que los valores y2 se alineen correctamente con sus valores y1 en el eje y?
eje gemelo
Se puede agregar un segundo eje y creando un eje doble,
ax2 = ax.twinx()
.
La escala de estos ejes se puede establecer utilizando sus límites,
ax2.set_ylim(y2min, y2max)
.
Los valores de
y2min, y2max
pueden calcularse utilizando alguna relación conocida (por ejemplo, implementada como una función) a partir de los límites del eje izquierdo.
import matplotlib.pyplot as plt
import numpy as np; np.random.seed(0)
x = np.linspace(0,50,101)
y = np.cumsum(np.random.normal(size=len(x)))+20.
fig, ax = plt.subplots()
ax2 = ax.twinx()
ax.plot(x,y, color="#dd0011")
ax.set_ylabel("Temperature [Celsius]")
ax2.set_ylabel("Temperature [Fahrenheit]")
# set twin scale (convert degree celsius to fahrenheit)
T_f = lambda T_c: T_c*1.8 + 32.
# get left axis limits
ymin, ymax = ax.get_ylim()
# apply function and set transformed values to right axis limits
ax2.set_ylim((T_f(ymin),T_f(ymax)))
# set an invisible artist to twin axes
# to prevent falling back to initial values on rescale events
ax2.plot([],[])
plt.show()
eje secundario
A partir de matplotlib 3.1 en adelante, se puede usar un yxis
secondary_yaxis
.
Esto se encarga de sincronizar los límites automáticamente.
Como entrada, uno necesita la función de conversión y su inverso.
import matplotlib.pyplot as plt
import numpy as np; np.random.seed(0)
x = np.linspace(0,50,101)
y = np.cumsum(np.random.normal(size=len(x)))+20.
# Convert celsius to Fahrenheit
T_f = lambda T_c: T_c*1.8 + 32.
# Convert Fahrenheit to Celsius
T_c = lambda T_f: (T_f - 32.)/1.8
fig, ax = plt.subplots()
ax2 = ax.secondary_yaxis("right", functions=(T_f, T_c))
ax.plot(x,y, color="#dd0011")
ax.set_ylabel("Temperature [Celsius]")
ax2.set_ylabel("Temperature [Fahrenheit]")
plt.show()
El resultado es el mismo que el anterior, pero como puede ver, uno no necesita establecer ningún límite.