Tensores, redes neuronales e imágenes
Contents
Tensores, redes neuronales e imágenes#
Introducción#
En esta lección nos acercamos al objeto de trabajo del aprendizaje profundo: la redes neuronales. La hacemos mostrando como usamos tensores para representar redes neuronales. Adicionalmente, veremos como usamos los tensores en la representación de imágenes, uno de los tipos de datos mas recurrente en la inteligencia artificial.
Redes Neuronales#
La siguiente imagen muestra el estado en un instante de una una parte oculta de una red neuronal profunda.
Fuente: Alvaro Montenegro
El proceso puede modelarse en forma simplificada usando matrices y vectores como se ve a continuación.
Observe por ejemplo que:
En la fase de entrenamiento de la red neuronal, los pesos de la matriz se van modificando hasta que se encuentra un óptimo local. Este proceso ocurre en toda la estructura de la red.
Por lo que no parece extraño que las GPU y las TPU pasen todo el tiempo haciendo operaciones de este tipo, que al final se reduce a sumas y multiplicaciones.
Por otro lado, lo que ocurre es que los objetos que se procesan no necesariamente son vectores como en el ejemplo, y esto lleva a la necesidad de generalizar los conceptos.
Imágenes a color#
De manera clásica una imagen a color está compuesta de tres colores primarios: rojo (Red), verde (Green) y azul (Blue). Para generar una imagen a color un computador maneja tres planos de color, los cuales son controlados desde tensores tridimensionales. Considere el siguiente ejemplo.
Fuente: Alvaro Montenegro
Cada pixel (punto) de la imagen es representado por una valor numérico en el rango de 0 a 255, o en rango de valores reales entre cero y 1.
Construcción aleatoria de una imagen#
Considere el siguiente código Python.
import numpy as np
I=np.random.randint(0,255,size=(3,10,10))
print(I)
[[[ 27 41 188 219 233 71 44 246 117 40]
[251 213 29 98 130 123 37 194 89 196]
[192 75 156 79 90 205 119 24 112 89]
[206 205 84 235 205 96 210 36 179 70]
[249 115 92 0 231 50 93 193 23 233]
[ 1 80 142 56 198 158 238 216 3 193]
[ 8 142 31 186 5 47 214 179 107 89]
[ 19 171 78 136 176 27 224 224 98 181]
[ 85 87 203 156 140 233 5 220 54 198]
[ 80 168 18 83 228 40 11 6 157 15]]
[[ 22 144 252 237 16 245 71 66 239 174]
[148 77 252 57 44 27 223 114 165 112]
[174 164 23 124 42 220 0 49 97 227]
[151 228 99 61 190 241 9 114 215 156]
[185 138 40 176 5 241 22 91 160 118]
[208 189 106 225 105 5 218 153 235 129]
[ 63 87 176 10 77 68 146 13 93 132]
[199 63 35 213 34 85 13 218 207 193]
[ 57 207 44 200 90 21 142 137 33 0]
[243 86 74 94 199 194 206 197 159 137]]
[[146 60 93 232 130 96 137 32 164 65]
[115 104 39 5 30 245 162 8 118 83]
[241 250 63 217 43 108 139 53 246 183]
[136 92 207 4 138 35 88 13 226 177]
[ 20 95 191 59 117 55 116 171 209 226]
[ 63 116 130 11 21 222 31 200 122 54]
[ 59 19 53 151 110 153 9 179 207 121]
[ 18 95 137 169 250 212 108 47 238 249]
[188 155 73 95 88 68 86 152 85 79]
[ 40 115 200 12 18 26 114 240 118 74]]]
Este tensor representa una imagen de tamaño \(10 \times 10\). Son tres planos de color \(10 \times 10\).
Observe que la primera dimensión corresponde a cada plano de color y las restantes dos dimensiones a las intensidades de cada color para cada punto.
Renderizar (dibujar en este caso), nos lleva a la siguiente imagen. Para esta sección require instalar matplotlib
# !conda install -c conda-forge matplotlib
import matplotlib.pyplot as plt
plt.imshow(I.T)
plt.show()
Observe que
(I.T).shape
(10, 10, 3)
Porque Python maneja las imágenes en este formato: Fila, columna y plano de color.
Imagen real#
Vamos a trabajar ahora con una imagen real. Para este ejercicio requiere instalar sklearn
.
# conda install -c anaconda scikit-image
import numpy as np
import matplotlib.pyplot as plt
from skimage import data
from skimage.color import rgb2gray
original = data.astronaut()
grayscale = rgb2gray(original)
fig, axes = plt.subplots(1, 2, figsize=(8, 4))
ax = axes.ravel()
ax[0].imshow(original)
ax[0].set_title("Original")
ax[1].imshow(grayscale, cmap=plt.cm.gray)
ax[1].set_title("Grayscale")
fig.tight_layout()
plt.show()
Idata=np.array(grayscale)
print("\nLa imagen tiene forma: ",Idata.shape,"\n")
print(Idata)
La imagen tiene forma: (512, 512)
[[5.83434902e-01 4.14859216e-01 2.44058431e-01 ... 4.75007843e-01
4.58213333e-01 4.69121961e-01]
[6.75588235e-01 5.56006667e-01 4.49052941e-01 ... 4.68548627e-01
4.56501176e-01 4.55958431e-01]
[7.66334902e-01 7.00524314e-01 6.49276078e-01 ... 4.76406667e-01
4.62104314e-01 4.53978431e-01]
...
[6.81696471e-01 6.81979216e-01 6.71889020e-01 ... 0.00000000e+00
2.82745098e-04 0.00000000e+00]
[6.74694510e-01 6.68532941e-01 6.64030196e-01 ... 2.82745098e-04
3.92156863e-03 0.00000000e+00]
[6.70482353e-01 6.63189804e-01 6.52838824e-01 ... 0.00000000e+00
3.92156863e-03 0.00000000e+00]]
Planos de color#
Idata = np.array(original)
print("\nLa imagen tiene forma: ",Idata.shape,"\n")
print("\nEscala de Rojos:\n\n",Idata[:511,:511,0],"\n")
print("\nEscala de Verdes:\n\n",Idata[:511,:511,1],"\n")
print("\nEscala de Azules:\n\n",Idata[:511,:511,2],"\n")
La imagen tiene forma: (512, 512, 3)
Escala de Rojos:
[[154 109 63 ... 126 127 120]
[177 144 113 ... 126 127 124]
[201 182 168 ... 125 128 126]
...
[186 188 184 ... 0 0 0]
[186 186 183 ... 2 0 0]
[183 182 185 ... 21 0 1]]
Escala de Verdes:
[[147 103 58 ... 120 120 117]
[171 141 114 ... 118 118 115]
[194 178 165 ... 119 120 116]
...
[169 169 167 ... 0 0 0]
[170 170 168 ... 2 0 0]
[169 167 164 ... 21 0 1]]
Escala de Azules:
[[151 124 102 ... 114 115 106]
[171 143 124 ... 111 112 108]
[193 175 164 ... 113 117 112]
...
[174 177 170 ... 0 0 1]
[176 177 170 ... 3 0 1]
[170 171 176 ... 16 1 1]]
fig, (ax1, ax2,ax3) = plt.subplots(1, 3,figsize=(15,15))
ax1.imshow(Idata[:,:,0],cmap="Reds")
ax1.set_xlabel('Red')
ax2.imshow(Idata[:,:,1],cmap="Greens")
ax2.set_xlabel('Green')
ax3.imshow(Idata[:,:,2],cmap="Blues")
ax3.set_xlabel('Blue')
plt.show()
Manipulación de imágenes#
Intercambia dos planos de color#
import numpy as np
import matplotlib.pyplot as plt
from skimage import data
from skimage.color import rgb2gray
original = data.astronaut()
Idata_m = Idata
Idata_m[:,:,0], Idata_m[:,:,2] = Idata_m[:,:,2], Idata_m[:,:,0]
fig, axes = plt.subplots(1, 2, figsize=(8, 4))
ax = axes.ravel()
ax[0].imshow(original)
ax[0].set_title("Original")
ax[1].imshow(Idata_m)
ax[1].set_title("Modificada")
fig.tight_layout()
plt.show()
Suma una constante a la imagen#
fig, axes = plt.subplots(1, 2, figsize=(8, 4))
ax = axes.ravel()
k = 10
ax[0].imshow(original)
ax[0].set_title("Original")
ax[1].imshow(original + k)
ax[1].set_title("Modificada")
fig.tight_layout()
plt.show()
fig, axes = plt.subplots(1, 2, figsize=(8, 4))
ax = axes.ravel()
k = 2
ax[0].imshow(original)
ax[0].set_title("Original")
ax[1].imshow(original //k)
ax[1].set_title("Modificada")
fig.tight_layout()
plt.show()
Idata_m = Idata
Idata_m[:,:,0 ]=0
fig, axes = plt.subplots(1, 2, figsize=(8, 4))
ax = axes.ravel()
ax[0].imshow(original)
ax[0].set_title("Original")
ax[1].imshow(Idata_m)
ax[1].set_title("Modificada")
fig.tight_layout()
plt.show()
Idata
array([[[ 0, 147, 151],
[ 0, 103, 124],
[ 0, 58, 102],
...,
[ 0, 120, 115],
[ 0, 117, 106],
[ 0, 119, 110]],
[[ 0, 171, 171],
[ 0, 141, 143],
[ 0, 114, 124],
...,
[ 0, 118, 112],
[ 0, 115, 108],
[ 0, 116, 105]],
[[ 0, 194, 193],
[ 0, 178, 175],
[ 0, 165, 164],
...,
[ 0, 120, 117],
[ 0, 116, 112],
[ 0, 114, 109]],
...,
[[ 0, 170, 176],
[ 0, 170, 177],
[ 0, 168, 170],
...,
[ 0, 0, 0],
[ 0, 0, 1],
[ 0, 0, 0]],
[[ 0, 169, 170],
[ 0, 167, 171],
[ 0, 164, 176],
...,
[ 0, 0, 1],
[ 0, 1, 1],
[ 0, 0, 0]],
[[ 0, 167, 172],
[ 0, 165, 169],
[ 0, 162, 171],
...,
[ 0, 0, 0],
[ 0, 1, 1],
[ 0, 0, 0]]], dtype=uint8)
fig, axes = plt.subplots(1, 2, figsize=(8, 4))
ax = axes.ravel()
ax[0].imshow(original)
ax[0].set_title("Original")
ax[1].imshow(255 - Idata)
ax[1].set_title("Modificada")
fig.tight_layout()
plt.show()
Colocar dos imagenes en un tensor#
Esta es una forma para organizar conjuntos de imágenes en un único tensor
original= np.expand_dims(original,axis=0)
original.shape
(1, 512, 512, 3)
Idata_m= np.expand_dims(Idata_m,axis=0)
images = np.concatenate((original, Idata_m),axis=0)
images.shape
(2, 512, 512, 3)
fig, axes = plt.subplots(1, 2, figsize=(8, 4))
ax = axes.ravel()
ax[0].imshow(images[0])
ax[0].set_title("Original")
ax[1].imshow(images[1])
ax[1].set_title("Modificada")
fig.tight_layout()
plt.show()
Ejercicios#
Baje una imagen de Internet y la almacena localmente, o léala por ejemplo del repositorio de Aprendizaje Profundo.
Lea la imagen. Apóyese en el siguiente código
Repita el tratamiento de la imagen como hicimos en la lección
La imagen del ave fue tomada originalmente de omes-va.com.
import matplotlib.pyplot as plt
import numpy as np
from skimage import io
file_1 = 'https://raw.githubusercontent.com/AprendizajeProfundo/Libro-Fundamentos/main/Fundamentacion_Matematica/Imagenes/ave.jpeg'
# Fuente: Esta es la imagen original tomada de [omes-va.com](https://omes-va.com/trasladar-rotar-escalar-recortar-una-imagen-opencv/). Código tomado del mismo sitio.
img_array=io.imread(file_1)
plt.imshow(img_array)
plt.show()
original = np.array(img_array)
original.shape
(426, 640, 3)