25
loading...
This website collects cookies to deliver better user experience
mkdir heatmap_calendar
cd heatmap_calendar
python3 -m venv venv
source venv/bin/activate
pip3 install matplotlib
rojo = (255, 0, 0)
verde = (0, 255, 0)
azul = (0, 0, 255)
valores = [
[rojo, verde, azul],
[verde, azul, rojo],
[azul, rojo, verde],
]
import matplotlib.pyplot as plt
rojo = (255, 0, 0)
verde = (0, 255, 0)
azul = (0, 0, 255)
valores = [
[rojo, verde, azul],
[verde, azul, rojo],
[azul, rojo, verde],
]
# Creamos el lienzo sobre el que dibujar las gráficas
fig, ax = plt.subplots()
# Mostramos la imagen que hemos definido
ax.imshow(valores)
plt.show()
import matplotlib.pyplot as plt
valores = [
[0, 175, 255],
[175, 255, 0],
[255, 0, 175],
]
fig, ax = plt.subplots()
# Indicamos a la función que la imagen es de escala de grises en lugar RGB (cmap='gray')
ax.imshow(valores, cmap='gray')
plt.show()
import matplotlib.pyplot as plt
valores = [
[10, 20, 30, 40, 50, 60, 70],
[20, 30, 40, 50, 60, 70, 10],
[30, 40, 50, 60, 70, 10, 20],
[40, 50, 60, 70, 10, 20, 30],
[50, 60, 70, 10, 20, 30, 40],
[60, 70, 10, 20, 30, 40, 50],
]
fig, ax = plt.subplots()
# Especificamos paleta de colores a usar y rango de valores a representar.
ax.imshow(valores, cmap='YlGn', vmin=0, vmax=100)
plt.show()
import matplotlib.pyplot as plt
# Lista de etiquetas para representar los días de la semana.
dias_semana = ['L', 'M', 'M', 'J', 'V', 'S', 'D']
valores = [
[10, 20, 30, 40, 50, 60, 70],
[20, 30, 40, 50, 60, 70, 10],
[30, 40, 50, 60, 70, 10, 20],
[40, 50, 60, 70, 10, 20, 30],
[50, 60, 70, 10, 20, 30, 40],
[60, 70, 10, 20, 30, 40, 50],
]
fig, ax = plt.subplots()
ax.imshow(valores, cmap='YlGn', vmin=0, vmax=100)
# Colocamos el título
ax.set_title("Enero\n")
# Borramos el contenido de las etiquetas del eje Y
ax.set_yticklabels([])
# Indicamos las posiciones posiciones del ejs X con las que secorresponden las etiquetas.
ax.set_xticks([0, 1, 2, 3, 4, 5, 6])
# Especificamos las etiquetas para las posiciones especificadas anteriormente.
ax.set_xticklabels(dias_semana)
plt.show()
import matplotlib.pyplot as plt
dias_semana = ['L', 'M', 'M', 'J', 'V', 'S', 'D']
valores = [
[10, 20, 30, 40, 50, 60, 70],
[20, 30, 40, 50, 60, 70, 10],
[30, 40, 50, 60, 70, 10, 20],
[40, 50, 60, 70, 10, 20, 30],
[50, 60, 70, 10, 20, 30, 40],
[60, 70, 10, 20, 30, 40, 50],
]
fig, ax = plt.subplots()
ax.imshow(valores, cmap='YlGn', vmin=0, vmax=100)
ax.set_title("Enero\n")
ax.set_yticklabels([])
ax.set_xticks([0, 1, 2, 3, 4, 5, 6])
ax.set_xticklabels(dias_semana)
# Colocamos las etiquetas del eje X en la parte superior
ax.xaxis.tick_top()
# Ocultamo cada uno de lso dados que circundan el gráfico
for lado in ['left', 'right', 'bottom', 'top']:
ax.spines[lado].set_visible(False)
plt.show()
import numpy as np
import matplotlib.pyplot as plt
# Colocaremos el valor especial de Not a Number a las cassila que sobran y
# conseguiremos que maptlotlib no las muestre
NA = np.nan
dias_semana = ['L', 'M', 'M', 'J', 'V', 'S', 'D']
valores = [
[NA, NA, NA, NA, NA, 60, 70],
[20, 30, 40, 50, 60, 70, 10],
[30, 40, 50, 60, 70, 10, 20],
[40, 50, 60, 70, 10, 20, 30],
[50, 60, 70, 10, 20, 30, 40],
[60, NA, NA, NA, NA, NA, NA],
]
fig, ax = plt.subplots()
ax.imshow(valores, cmap='YlGn', vmin=0, vmax=100)
ax.set_title("Enero\n")
ax.set_yticklabels([])
ax.set_xticks([0, 1, 2, 3, 4, 5, 6])
ax.set_xticklabels(dias_semana)
ax.xaxis.tick_top()
# Reducimos la longitud de las marcas a 0 para que no sean visibles
ax.tick_params(axis=u'both', which=u'both', length=0)
for lado in ['left', 'right', 'bottom', 'top']:
ax.spines[lado].set_visible(False)
plt.show()
import numpy as np
import matplotlib.pyplot as plt
NA = np.nan
dias_semana = ['L', 'M', 'M', 'J', 'V', 'S', 'D']
valores = [
[NA, NA, NA, NA, NA, 60, 70],
[20, 30, 40, 50, 60, 70, 10],
[30, 40, 50, 60, 70, 10, 20],
[40, 50, 60, 70, 10, 20, 30],
[50, 60, 70, 10, 20, 30, 40],
[60, NA, NA, NA, NA, NA, NA],
]
fig, ax = plt.subplots()
ax.imshow(valores, cmap='YlGn', vmin=0, vmax=100)
ax.set_title("Enero\n")
ax.set_yticklabels([])
ax.set_xticks([0, 1, 2, 3, 4, 5, 6])
ax.set_xticklabels(dias_semana)
ax.xaxis.tick_top()
ax.tick_params(axis=u'both', which=u'both', length=0)
for lado in ['left', 'right', 'bottom', 'top']:
ax.spines[lado].set_visible(False)
# Indicamos las posiciones donde dibujaremos la rejilla
ax.set_xticks([-0,5, 0.5, 1.5, 2.5, 3.5, 4.5, 5.5, 6.5], minor=True)
ax.set_yticks([-0,5, 0.5, 1.5, 2.5, 3.5, 4.5, 5,5], minor=True)
# Dibujamos la rejilla de color blanco para que actue como separador.
ax.grid(which='minor', color='w', linestyle='-', linewidth=2)
plt.show()
import calendar
import numpy as np
import matplotlib.pyplot as plt
def heatmap_calendar(year, valores):
dias_semana = ['L', 'M', 'M', 'J', 'V', 'S', 'D']
nombres_meses = ['Enero', 'Febrero', 'Marzo', 'Abril', 'Mayo', 'Junio', 'Julio', 'Agosto', 'Septiembre', 'Octubre', 'Noviembre', 'Diciembre']
maximo_semanas_mes = 6
meses = 12
columnas = 3
filas = 4
# Creamos un gráfico para cada més del año
fig, ax = plt.subplots(filas, columnas, figsize=(3.5*columnas, 3.5*filas))
# Para facilitar la iteración convertimos la tabla 2D en una lista 1D
axs = np.array(ax).reshape(-1)
numero_valores = len(valores)
maximo = max(valores)
puntero_dia_actual = 0
# Repetimos el proceso para cada mes
for mes in range(meses):
# Averiguamos que día de la semana empieza el mes y cuantos días tiene
dia_semana, dias_mes = calendar.monthrange(year, mes + 1)
# Creamos un array nullo como plantilla para ir colocando los valores del mes
plantilla_mes = np.empty((maximo_semanas_mes, len(dias_semana)))
plantilla_mes[:] = np.nan
# Mostramos nombre del mes
axs[mes].set_title(nombres_meses[mes]+'\n', fontsize=12)
# Colocamos etiqueta de días de la semana.
axs[mes].set_xticks(np.arange(len(dias_semana)))
axs[mes].set_xticklabels(dias_semana, fontsize=10, fontweight='bold', color='#555555')
axs[mes].set_yticklabels([])
axs[mes].xaxis.tick_top()
# Ocultamos las marcas de los ejes
axs[mes].tick_params(axis=u'both', which=u'both', length=0) # remove tick marks
# Dibujamos rejilla blanca para separar casillas
axs[mes].set_xticks(np.arange(-.5, len(dias_semana), 1), minor=True)
axs[mes].set_yticks(np.arange(-.5, maximo_semanas_mes, 1), minor=True)
axs[mes].grid(which='minor', color='w', linestyle='-', linewidth=2)
# Ocultamos cada uno de los lados del marco que rodea la cuadrícula.
for lado in ['left', 'right', 'bottom', 'top']:
axs[mes].spines[lado].set_visible(False)
# Empezamos a rellenar cada mes desde la primera fila y desde el día de la
# semana en la que empieza el mes
fila = 0
columna = dia_semana
# Copiamos tantos valores de nuestra lista como días tiene el mes
for n in range(dias_mes):
if puntero_dia_actual < numero_valores:
plantilla_mes[fila][columna] = valores[puntero_dia_actual]
# Conservamos cual es el próximo valor de nuestra lista a procesar
puntero_dia_actual += 1
# Controlamos cuando se produce cambio de semana
if columna == 6:
columna = 0
fila +=1
else:
columna += 1
# Mostramos los valores del mes
axs[mes].imshow(plantilla_mes, cmap='YlGn', vmin=1, vmax=maximo)
# Colocamos el año del calendario y reajustamos el conjunto para dejas
# un pequeño margen alrededor
fig.suptitle("\n" + str(year), fontsize=16)
plt.subplots_adjust(left=0.04, right=0.96, top=0.88, bottom=0.04)
# La visualización online es correcta en el caso de jupyter notebook, pero hay solapamientos
# incorrectos si lo vemos directamente con el visor de matplotlib. Salvamos en un documento PDF
# para tener la salida correcta
plt.savefig('heatmap_calendar.pdf')
plt.show()
if __name__ == '__main__':
# Generamos valores aleatorios para probar la función
valores = np.random.randint(500, size=365)
heatmap_calendar(2021, valores=valores)