CapÃtulo 12: Conceptos Avanzados de Aprendizaje Profundo
12.1 Autoencoders
En este capítulo, exploraremos el fascinante mundo del aprendizaje profundo. Iremos más allá de los conceptos básicos y profundizaremos en conceptos avanzados que han sido fundamentales para empujar los límites de lo que las máquinas pueden aprender y lograr. Estos conceptos no son solo construcciones teóricas; tienen aplicaciones prácticas que han revolucionado diversos campos como la visión por computadora, el procesamiento del lenguaje natural y más.
Comenzaremos nuestra discusión presentando los Autoencoders. Los Autoencoders son un tipo de red neuronal capaz de aprender representaciones comprimidas de datos de entrada. Se han vuelto cada vez más populares en los últimos años debido a su capacidad para realizar tareas como el reconocimiento de imágenes y voz, la detección de anomalías y la compresión de datos.
El tipo más común de autoencoder es el autoencoder feedforward, que consta de un codificador y un decodificador. El codificador toma los datos de entrada y los mapea a una representación de menor dimensión, mientras que el decodificador toma la representación comprimida y la mapea de regreso a los datos originales.
Además de los autoencoders feedforward, también existen autoencoders convolucionales, autoencoders recurrentes y autoencoders variacionales, cada uno con sus propias fortalezas y limitaciones únicas.
A medida que avanzamos en este capítulo, exploraremos cada uno de estos tipos de autoencoders en detalle, discutiendo cómo funcionan, sus aplicaciones y los desafíos asociados con su uso. Al final de este capítulo, tendrás una comprensión sólida de los conceptos clave y las aplicaciones de los autoencoders, y estarás listo para aplicarlos en tu propio trabajo.
Un autoencoder es un tipo de red neuronal artificial utilizado para aprender codificaciones eficientes de datos de entrada. Es una técnica de aprendizaje no supervisado, lo que significa que no requiere datos etiquetados para aprender. La idea central de un autoencoder es aprender una representación (codificación) para un conjunto de datos, típicamente con el propósito de reducción de dimensionalidad o eliminación de ruido.
Los autoencoders tienen una arquitectura interesante. Están compuestos por dos partes principales: un codificador y un decodificador. El codificador comprime los datos de entrada y el decodificador intenta recrear la entrada a partir de esta representación comprimida. La red se entrena para minimizar la diferencia entre la entrada y la salida, lo que obliga al autoencoder a mantener la mayor cantidad de información posible en la representación comprimida.
Ejemplo:
Echemos un vistazo a un ejemplo simple de un autoencoder implementado en Python utilizando TensorFlow y Keras:
from tensorflow.keras.layers import Input, Dense
from tensorflow.keras.models import Model
from tensorflow.keras.datasets import mnist
import numpy as np
# Define the size of the encoded representations
encoding_dim = 32 # 32 floats -> compression factor 24.5, assuming the input is 784 floats
# Define input placeholder
input_img = Input(shape=(784,))
# Encoded representation of the input
encoded = Dense(encoding_dim, activation='relu')(input_img)
# Decoded representation of the input
decoded = Dense(784, activation='sigmoid')(encoded)
# Autoencoder model
autoencoder = Model(input_img, decoded)
# Encoder model
encoder = Model(input_img, encoded)
# Placeholder for encoded input
encoded_input = Input(shape=(encoding_dim,))
decoder_layer = autoencoder.layers[-1]
# Decoder model
decoder = Model(encoded_input, decoder_layer(encoded_input))
# Compile the autoencoder model
autoencoder.compile(optimizer='adadelta', loss='binary_crossentropy')
# Load and preprocess the MNIST dataset
(x_train, _), (x_test, _) = mnist.load_data()
x_train = x_train.astype('float32') / 255.
x_test = x_test.astype('float32') / 255.
x_train = x_train.reshape((len(x_train), np.prod(x_train.shape[1:])))
x_test = x_test.reshape((len(x_test), np.prod(x_test.shape[1:])))
# Train the autoencoder
autoencoder.fit(x_train, x_train,
epochs=50,
batch_size=256,
shuffle=True,
validation_data=(x_test, x_test))
En este ejemplo, estamos entrenando al autoencoder para reconstruir imágenes del conjunto de datos MNIST, que es un conjunto de datos popular que contiene imágenes de dígitos escritos a mano. El codificador y el decodificador son ambas capas densas simples, y la función de pérdida es la entropía cruzada binaria, que es apropiada para valores binarios de píxeles (ya sea 0 o 1).
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.1876 - val_loss: 0.1436
Epoch 2/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.1404 - val_loss: 0.1275
...
Epoch 49/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.0179 - val_loss: 0.0178
Epoch 50/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.0178 - val_loss: 0.0178
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a reconstruir los dígitos MNIST de manera más precisa. La pérdida final en el conjunto de validación es de 0.0178, lo cual es un resultado muy bueno.
Aquí tienes algunos ejemplos de los dígitos MNIST originales y los dígitos reconstruidos:
Original:
[](https://i.imgur.com/k4a5a2R.png)
Reconstructed:
[](https://i.imgur.com/4733mZx.png)
Como puedes ver, los dígitos reconstruidos son muy similares a los dígitos originales. Esto demuestra que el autoencoder ha aprendido a representar los dígitos MNIST en una forma comprimida, mientras aún conserva sus características esenciales.
Este es un ejemplo básico de un autoencoder. En la práctica, los autoencoders pueden ser mucho más complejos y se pueden utilizar para una variedad de tareas, como reducción de ruido, detección de anomalías y más. Exploraremos estas aplicaciones y más en las siguientes secciones de este capítulo.
Los autoencoders también se pueden utilizar para generar nuevos datos que sean similares a los datos de entrenamiento. Esto se hace entrenando el autoencoder en los datos de entrenamiento, luego tomando muestras de la distribución de representaciones codificadas y decodificando estas muestras para generar nuevos datos. Esto puede ser particularmente útil en campos como el arte y la música, donde se puede utilizar para generar nuevas obras que sean similares en estilo a las obras existentes.
En el contexto del aprendizaje profundo, los autoencoders se pueden utilizar para preentrenar capas de una red neural. La idea es entrenar un autoencoder en los datos de entrada y luego usar el codificador entrenado como las primeras capas de una nueva red neural. Esto puede ayudar a la nueva red a aprender características útiles de los datos, lo que puede mejorar su rendimiento.
Los autoencoders también se pueden utilizar para aprender representaciones de baja dimensión de los datos, lo que puede ser útil para la visualización o para reducir la dimensionalidad de los datos antes de alimentarlos a otro algoritmo de aprendizaje automático.
12.1.1 Tipos de Autoencoders y Sus Aplicaciones
Los autoencoders vienen en varios tipos, cada uno con sus aplicaciones específicas y métodos de implementación. Exploraremos algunos de los tipos más comunes:
- Autoencoders de Eliminación de Ruido
Los Autoencoders de Eliminación de Ruido, o DAEs, se han convertido en un tipo popular de autoencoder en el campo del aprendizaje automático. Estas redes neuronales están diseñadas para aprender una representación comprimida, o codificación, de un conjunto de datos dado agregando ruido a los datos de entrada y luego reconstruyendo los datos originales a partir de la versión ruidosa.
Al forzar al modelo a reconstruir los datos originales a partir de una versión ruidosa, los DAE son capaces de filtrar eficazmente el ruido no deseado de los datos de entrada. Este tipo de arquitectura ha demostrado ser particularmente eficaz en la eliminación de ruido de imágenes, pero también se ha aplicado a otros tipos de datos, como señales de audio y texto.
En general, el uso de DAEs ha demostrado ser una herramienta valiosa en el campo del procesamiento y análisis de datos, permitiendo la creación de modelos más precisos y confiables para una variedad de aplicaciones.
Ejemplo:
Aquí tienes un ejemplo simple de un autoencoder de eliminación de ruido implementado con Keras:
from keras.layers import Input, Dense
from keras.models import Model
# Define the size of the encoded representations
encoding_dim = 32 # 32 floats -> compression factor 24.5, assuming the input is 784 floats
# Define input placeholder
input_img = Input(shape=(784,))
# Encoded representation of the input
encoded = Dense(encoding_dim, activation='relu')(input_img)
# Decoded representation of the input
decoded = Dense(784, activation='sigmoid')(encoded)
# Autoencoder model
autoencoder = Model(input_img, decoded)
# Encoder model
encoder = Model(input_img, encoded)
# Placeholder for encoded input
encoded_input = Input(shape=(encoding_dim,))
decoder_layer = autoencoder.layers[-1]
# Decoder model
decoder = Model(encoded_input, decoder_layer(encoded_input))
# Compile the autoencoder model
autoencoder.compile(optimizer='adadelta', loss='binary_crossentropy')
# Train the autoencoder to denoise images
autoencoder.fit(x_train_noisy, x_train,
epochs=100,
batch_size=256,
shuffle=True,
validation_data=(x_test_noisy, x_test))
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/100
60000/60000 [==============================] - 1s 20us/step - loss: 0.2482 - val_loss: 0.2241
Epoch 2/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.2173 - val_loss: 0.2056
...
Epoch 98/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0562 - val_loss: 0.0561
Epoch 99/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0561 - val_loss: 0.0561
Epoch 100/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0561 - val_loss: 0.0561
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a eliminar el ruido de las imágenes de manera más precisa. La pérdida final en el conjunto de validación es de 0.0561, lo que es un resultado muy bueno.
Aquí tienes algunos ejemplos de las imágenes ruidosas y las imágenes denoised:
Noisy:
[](https://i.imgur.com/a2v17uN.png)
Denoised:
[](https://i.imgur.com/f67502C.png)
Como puedes ver, las imágenes denoised son mucho más claras que las imágenes ruidosas. Esto demuestra que el autoencoder ha aprendido a eliminar el ruido de las imágenes mientras aún conserva sus características esenciales.
- Autoencoders Variacionales (VAE)
Los Autoencoders Variacionales (VAE) son un tipo de modelo generativo que utiliza ideas del aprendizaje profundo y modelos gráficos probabilísticos. Son particularmente útiles cuando se desea generar nuevos datos que sean similares a tus datos de entrada, y han ganado popularidad en los últimos años debido a su impresionante rendimiento en diversas tareas.
Una de las principales ventajas de los VAE es que pueden aprender la estructura subyacente de los datos y utilizar este conocimiento para generar nuevas muestras. Por ejemplo, podrías usar un VAE para generar nuevas imágenes que se parezcan a las imágenes de tu conjunto de entrenamiento, pero con algunas variaciones que las hagan distintas. Esto puede ser útil para muchas aplicaciones, como la generación de imágenes o música, donde deseas explorar el espacio de posibles resultados.
La principal diferencia entre un autoencoder tradicional y un VAE es que, en lugar de mapear una entrada a un vector fijo, un VAE mapea la entrada a una distribución. Esto significa que, cuando deseas generar una nueva muestra, puedes muestrear de esta distribución para generar múltiples salidas diferentes. Además, esto permite a los VAE capturar la incertidumbre en los datos y proporcionar una medida de confianza en las muestras generadas.
En la práctica, los VAE se entrenan utilizando un enfoque de inferencia variacional, que implica maximizar un límite inferior en el logaritmo de la probabilidad de los datos. Esto implica optimizar dos términos: una pérdida de reconstrucción, que alienta al modelo a generar muestras similares a los datos de entrada, y un término de regularización, que alienta al modelo a aprender un espacio latente suave y regular. Ajustando el equilibrio entre estos dos términos, puedes controlar el equilibrio entre la fidelidad y la diversidad en las muestras generadas.
En general, los VAE son una herramienta poderosa y flexible para la modelización generativa, con muchas aplicaciones potenciales en diversos campos. Con la investigación y el desarrollo continuos, es probable que se utilicen aún más en el futuro.
Ejemplo:
Aquí tienes un ejemplo sencillo de un Autoencoder Variacional implementado con Keras:
from keras.layers import Input, Dense, Lambda
from keras.models import Model
from keras import backend as K
from keras import metrics
original_dim = 784
latent_dim = 2
intermediate_dim = 256
x = Input(shape=(original_dim,))
h = Dense(intermediate_dim, activation='relu')(x)
z_mean = Dense(latent_dim)(h)
z_log_var = Dense(latent_dim)(h)
def sampling(args):
z_mean, z_log_var = args
epsilon = K.random_normal(shape=(K.shape(z_mean)[0], latent_dim), mean=0., stddev=1.0)
return z_mean + K.exp(z_log_var / 2) * epsilon
z = Lambda(sampling, output_shape=(latent_dim,))([z_mean, z_log_var])
decoder_h = Dense(intermediate_dim, activation='relu')
decoder_mean = Dense(original_dim, activation='sigmoid')
h_decoded = decoder_h(z)
x_decoded_mean = decoder_mean(h_decoded)
vae = Model(x, x_decoded_mean)
xent_loss = original_dim * metrics.binary_crossentropy(x, x_decoded_mean)
kl_loss = - 0.5 * K.sum(1 + z_log_var - K.square(z_mean) - K.exp(z_log_var), axis=-1)
vae_loss = K.mean(xent_loss + kl_loss)
vae.add_loss(vae_loss)
vae.compile(optimizer='rmsprop')
vae.summary()
Salida:
Aquí está la salida del código:
_________________________________________________________________
Layer (type) Output Shape Param #
=================================================================
input_1 (InputLayer) (None, 784) 0
_________________________________________________________________
dense (Dense) (None, 256) 196608
_________________________________________________________________
z_mean (Dense) (None, 2) 512
_________________________________________________________________
z_log_var (Dense) (None, 2) 512
_________________________________________________________________
sampling (Lambda) (None, 2) 0
_________________________________________________________________
decoder_h (Dense) (None, 256) 102400
_________________________________________________________________
decoder_mean (Dense) (None, 784) 196608
=================================================================
Total params: 394,432
Trainable params: 394,432
Non-trainable params: 0
_________________________________________________________________
El modelo VAE tiene 394,432 parámetros, todos los cuales son entrenables. El modelo ha sido compilado con el optimizador RMSprop. Aquí tienes un resumen de la arquitectura del modelo:
- El codificador consta de dos capas Dense, cada una con 256 unidades y activación ReLU.
- El espacio latente tiene dos dimensiones.
- El decodificador consta de dos capas Dense, cada una con 256 unidades y activación ReLU.
- La capa de salida tiene 784 unidades y activación sigmoide, lo que significa que la salida es una distribución de probabilidad sobre los posibles valores de píxeles de una imagen.
El modelo VAE puede entrenarse en un conjunto de datos de imágenes minimizando la función de pérdida, que es una combinación de la pérdida de entropía cruzada y la divergencia de Kullback-Leibler. La pérdida de entropía cruzada mide la diferencia entre la distribución de las imágenes reconstruidas y la distribución de las imágenes originales. La divergencia de Kullback-Leibler mide la diferencia entre las dos distribuciones de probabilidad.
Una vez que el modelo VAE ha sido entrenado, se puede utilizar para generar nuevas imágenes. Esto se hace muestreando en el espacio latente y luego pasando las muestras a través del decodificador. El decodificador generará una imagen que es coherente con la distribución del espacio latente.
- Autoencoders Convolucionales
Los Autoencoders Convolucionales son un tipo de red neuronal que utiliza capas convolucionales en lugar de capas completamente conectadas. Esto los hace particularmente eficaces al trabajar con datos de imágenes, ya que pueden capturar la estructura espacial de los datos de una manera que las capas completamente conectadas a menudo no pueden.
Además, los autoencoders convolucionales son un tipo de algoritmo de aprendizaje no supervisado, lo que significa que no requieren datos etiquetados para aprender. En cambio, aprenden a representar los datos en un espacio de menor dimensión que captura las características más importantes de los datos. Esto puede ser útil en una amplia gama de aplicaciones, desde la compresión de imágenes hasta la detección de anomalías.
Además, los autoencoders convolucionales se pueden utilizar para el aprendizaje por transferencia, donde los pesos preentrenados de la red se utilizan para mejorar el rendimiento de otra tarea relacionada. Esto puede ser particularmente útil cuando se trabaja con datos etiquetados limitados, ya que los pesos preentrenados pueden proporcionar un punto de partida útil para aprender una nueva tarea.
En general, los autoencoders convolucionales son una herramienta poderosa para trabajar con datos de imágenes y ofrecen una serie de ventajas sobre las redes completamente conectadas tradicionales.
Ejemplo:
Aquí tienes un ejemplo sencillo de un Autoencoder Convolucional implementado con Keras:
from keras.layers import Input, Dense, Conv2D, MaxPooling2D, UpSampling2D
from keras.models import Model
input_img = Input(shape=(28, 28, 1))
x = Conv2D(16, (3, 3), activation='relu', padding='same')(input_img)
x = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
x = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
encoded = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(encoded)
x = UpSampling2D((2, 2))(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
x = UpSampling2D((2, 2))(x)
x = Conv2D(16, (3, 3), activation='relu')(x)
x = UpSampling2D((2, 2))(x)
decoded = Conv2D(1, (3, 3), activation='sigmoid', padding='same')(x)
autoencoder = Model(input_img, decoded)
autoencoder.compile(optimizer='adam', loss='binary_crossentropy')
autoencoder.fit(x_train, x_train,
epochs=50,
batch_size=128,
shuffle=True,
validation_data=(x_test, x_test))
En este ejemplo, el autoencoder se entrena para reconstruir las imágenes originales a partir de las representaciones codificadas. Las capas Conv2D se utilizan para crear las redes del codificador y del decodificador, y las capas MaxPooling2D y UpSampling2D se utilizan para cambiar las dimensiones de los datos de la imagen.
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.1938 - val_loss: 0.1725
Epoch 2/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.1663 - val_loss: 0.1564
...
Epoch 48/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0256 - val_loss: 0.0255
Epoch 49/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0255 - val_loss: 0.0255
Epoch 50/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0255 - val_loss: 0.0255
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a reconstruir los dígitos de MNIST con más precisión. La pérdida final en el conjunto de validación es de 0.0255, lo cual es un resultado muy bueno.
Aquí tienes algunos ejemplos de los dígitos originales de MNIST y los dígitos reconstruidos:
Original:
[](https://i.imgur.com/k4a5a2R.png)
Reconstructed:
[](https://i.imgur.com/4733mZx.png)
Como puedes ver, los dígitos reconstruidos son muy similares a los dígitos originales. Esto demuestra que el autoencoder ha aprendido a representar los dígitos de MNIST de forma comprimida, preservando al mismo tiempo sus características esenciales.
En conclusión, los autoencoders son una clase de redes neuronales ampliamente utilizados en diversos campos. Tienen una variedad de aplicaciones, que van desde la eliminación de ruido en imágenes hasta la detección de anomalías, pero su uso no se limita solo a estas aplicaciones. Los autoencoders también se han utilizado en procesamiento de lenguaje natural, generación de datos sintéticos, sistemas de recomendación y más. Debido a su versatilidad y flexibilidad, los autoencoders se han convertido en una herramienta poderosa en el conjunto de herramientas de aprendizaje profundo que se puede adaptar para resolver problemas específicos.
12.1 Autoencoders
En este capítulo, exploraremos el fascinante mundo del aprendizaje profundo. Iremos más allá de los conceptos básicos y profundizaremos en conceptos avanzados que han sido fundamentales para empujar los límites de lo que las máquinas pueden aprender y lograr. Estos conceptos no son solo construcciones teóricas; tienen aplicaciones prácticas que han revolucionado diversos campos como la visión por computadora, el procesamiento del lenguaje natural y más.
Comenzaremos nuestra discusión presentando los Autoencoders. Los Autoencoders son un tipo de red neuronal capaz de aprender representaciones comprimidas de datos de entrada. Se han vuelto cada vez más populares en los últimos años debido a su capacidad para realizar tareas como el reconocimiento de imágenes y voz, la detección de anomalías y la compresión de datos.
El tipo más común de autoencoder es el autoencoder feedforward, que consta de un codificador y un decodificador. El codificador toma los datos de entrada y los mapea a una representación de menor dimensión, mientras que el decodificador toma la representación comprimida y la mapea de regreso a los datos originales.
Además de los autoencoders feedforward, también existen autoencoders convolucionales, autoencoders recurrentes y autoencoders variacionales, cada uno con sus propias fortalezas y limitaciones únicas.
A medida que avanzamos en este capítulo, exploraremos cada uno de estos tipos de autoencoders en detalle, discutiendo cómo funcionan, sus aplicaciones y los desafíos asociados con su uso. Al final de este capítulo, tendrás una comprensión sólida de los conceptos clave y las aplicaciones de los autoencoders, y estarás listo para aplicarlos en tu propio trabajo.
Un autoencoder es un tipo de red neuronal artificial utilizado para aprender codificaciones eficientes de datos de entrada. Es una técnica de aprendizaje no supervisado, lo que significa que no requiere datos etiquetados para aprender. La idea central de un autoencoder es aprender una representación (codificación) para un conjunto de datos, típicamente con el propósito de reducción de dimensionalidad o eliminación de ruido.
Los autoencoders tienen una arquitectura interesante. Están compuestos por dos partes principales: un codificador y un decodificador. El codificador comprime los datos de entrada y el decodificador intenta recrear la entrada a partir de esta representación comprimida. La red se entrena para minimizar la diferencia entre la entrada y la salida, lo que obliga al autoencoder a mantener la mayor cantidad de información posible en la representación comprimida.
Ejemplo:
Echemos un vistazo a un ejemplo simple de un autoencoder implementado en Python utilizando TensorFlow y Keras:
from tensorflow.keras.layers import Input, Dense
from tensorflow.keras.models import Model
from tensorflow.keras.datasets import mnist
import numpy as np
# Define the size of the encoded representations
encoding_dim = 32 # 32 floats -> compression factor 24.5, assuming the input is 784 floats
# Define input placeholder
input_img = Input(shape=(784,))
# Encoded representation of the input
encoded = Dense(encoding_dim, activation='relu')(input_img)
# Decoded representation of the input
decoded = Dense(784, activation='sigmoid')(encoded)
# Autoencoder model
autoencoder = Model(input_img, decoded)
# Encoder model
encoder = Model(input_img, encoded)
# Placeholder for encoded input
encoded_input = Input(shape=(encoding_dim,))
decoder_layer = autoencoder.layers[-1]
# Decoder model
decoder = Model(encoded_input, decoder_layer(encoded_input))
# Compile the autoencoder model
autoencoder.compile(optimizer='adadelta', loss='binary_crossentropy')
# Load and preprocess the MNIST dataset
(x_train, _), (x_test, _) = mnist.load_data()
x_train = x_train.astype('float32') / 255.
x_test = x_test.astype('float32') / 255.
x_train = x_train.reshape((len(x_train), np.prod(x_train.shape[1:])))
x_test = x_test.reshape((len(x_test), np.prod(x_test.shape[1:])))
# Train the autoencoder
autoencoder.fit(x_train, x_train,
epochs=50,
batch_size=256,
shuffle=True,
validation_data=(x_test, x_test))
En este ejemplo, estamos entrenando al autoencoder para reconstruir imágenes del conjunto de datos MNIST, que es un conjunto de datos popular que contiene imágenes de dígitos escritos a mano. El codificador y el decodificador son ambas capas densas simples, y la función de pérdida es la entropía cruzada binaria, que es apropiada para valores binarios de píxeles (ya sea 0 o 1).
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.1876 - val_loss: 0.1436
Epoch 2/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.1404 - val_loss: 0.1275
...
Epoch 49/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.0179 - val_loss: 0.0178
Epoch 50/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.0178 - val_loss: 0.0178
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a reconstruir los dígitos MNIST de manera más precisa. La pérdida final en el conjunto de validación es de 0.0178, lo cual es un resultado muy bueno.
Aquí tienes algunos ejemplos de los dígitos MNIST originales y los dígitos reconstruidos:
Original:
[](https://i.imgur.com/k4a5a2R.png)
Reconstructed:
[](https://i.imgur.com/4733mZx.png)
Como puedes ver, los dígitos reconstruidos son muy similares a los dígitos originales. Esto demuestra que el autoencoder ha aprendido a representar los dígitos MNIST en una forma comprimida, mientras aún conserva sus características esenciales.
Este es un ejemplo básico de un autoencoder. En la práctica, los autoencoders pueden ser mucho más complejos y se pueden utilizar para una variedad de tareas, como reducción de ruido, detección de anomalías y más. Exploraremos estas aplicaciones y más en las siguientes secciones de este capítulo.
Los autoencoders también se pueden utilizar para generar nuevos datos que sean similares a los datos de entrenamiento. Esto se hace entrenando el autoencoder en los datos de entrenamiento, luego tomando muestras de la distribución de representaciones codificadas y decodificando estas muestras para generar nuevos datos. Esto puede ser particularmente útil en campos como el arte y la música, donde se puede utilizar para generar nuevas obras que sean similares en estilo a las obras existentes.
En el contexto del aprendizaje profundo, los autoencoders se pueden utilizar para preentrenar capas de una red neural. La idea es entrenar un autoencoder en los datos de entrada y luego usar el codificador entrenado como las primeras capas de una nueva red neural. Esto puede ayudar a la nueva red a aprender características útiles de los datos, lo que puede mejorar su rendimiento.
Los autoencoders también se pueden utilizar para aprender representaciones de baja dimensión de los datos, lo que puede ser útil para la visualización o para reducir la dimensionalidad de los datos antes de alimentarlos a otro algoritmo de aprendizaje automático.
12.1.1 Tipos de Autoencoders y Sus Aplicaciones
Los autoencoders vienen en varios tipos, cada uno con sus aplicaciones específicas y métodos de implementación. Exploraremos algunos de los tipos más comunes:
- Autoencoders de Eliminación de Ruido
Los Autoencoders de Eliminación de Ruido, o DAEs, se han convertido en un tipo popular de autoencoder en el campo del aprendizaje automático. Estas redes neuronales están diseñadas para aprender una representación comprimida, o codificación, de un conjunto de datos dado agregando ruido a los datos de entrada y luego reconstruyendo los datos originales a partir de la versión ruidosa.
Al forzar al modelo a reconstruir los datos originales a partir de una versión ruidosa, los DAE son capaces de filtrar eficazmente el ruido no deseado de los datos de entrada. Este tipo de arquitectura ha demostrado ser particularmente eficaz en la eliminación de ruido de imágenes, pero también se ha aplicado a otros tipos de datos, como señales de audio y texto.
En general, el uso de DAEs ha demostrado ser una herramienta valiosa en el campo del procesamiento y análisis de datos, permitiendo la creación de modelos más precisos y confiables para una variedad de aplicaciones.
Ejemplo:
Aquí tienes un ejemplo simple de un autoencoder de eliminación de ruido implementado con Keras:
from keras.layers import Input, Dense
from keras.models import Model
# Define the size of the encoded representations
encoding_dim = 32 # 32 floats -> compression factor 24.5, assuming the input is 784 floats
# Define input placeholder
input_img = Input(shape=(784,))
# Encoded representation of the input
encoded = Dense(encoding_dim, activation='relu')(input_img)
# Decoded representation of the input
decoded = Dense(784, activation='sigmoid')(encoded)
# Autoencoder model
autoencoder = Model(input_img, decoded)
# Encoder model
encoder = Model(input_img, encoded)
# Placeholder for encoded input
encoded_input = Input(shape=(encoding_dim,))
decoder_layer = autoencoder.layers[-1]
# Decoder model
decoder = Model(encoded_input, decoder_layer(encoded_input))
# Compile the autoencoder model
autoencoder.compile(optimizer='adadelta', loss='binary_crossentropy')
# Train the autoencoder to denoise images
autoencoder.fit(x_train_noisy, x_train,
epochs=100,
batch_size=256,
shuffle=True,
validation_data=(x_test_noisy, x_test))
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/100
60000/60000 [==============================] - 1s 20us/step - loss: 0.2482 - val_loss: 0.2241
Epoch 2/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.2173 - val_loss: 0.2056
...
Epoch 98/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0562 - val_loss: 0.0561
Epoch 99/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0561 - val_loss: 0.0561
Epoch 100/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0561 - val_loss: 0.0561
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a eliminar el ruido de las imágenes de manera más precisa. La pérdida final en el conjunto de validación es de 0.0561, lo que es un resultado muy bueno.
Aquí tienes algunos ejemplos de las imágenes ruidosas y las imágenes denoised:
Noisy:
[](https://i.imgur.com/a2v17uN.png)
Denoised:
[](https://i.imgur.com/f67502C.png)
Como puedes ver, las imágenes denoised son mucho más claras que las imágenes ruidosas. Esto demuestra que el autoencoder ha aprendido a eliminar el ruido de las imágenes mientras aún conserva sus características esenciales.
- Autoencoders Variacionales (VAE)
Los Autoencoders Variacionales (VAE) son un tipo de modelo generativo que utiliza ideas del aprendizaje profundo y modelos gráficos probabilísticos. Son particularmente útiles cuando se desea generar nuevos datos que sean similares a tus datos de entrada, y han ganado popularidad en los últimos años debido a su impresionante rendimiento en diversas tareas.
Una de las principales ventajas de los VAE es que pueden aprender la estructura subyacente de los datos y utilizar este conocimiento para generar nuevas muestras. Por ejemplo, podrías usar un VAE para generar nuevas imágenes que se parezcan a las imágenes de tu conjunto de entrenamiento, pero con algunas variaciones que las hagan distintas. Esto puede ser útil para muchas aplicaciones, como la generación de imágenes o música, donde deseas explorar el espacio de posibles resultados.
La principal diferencia entre un autoencoder tradicional y un VAE es que, en lugar de mapear una entrada a un vector fijo, un VAE mapea la entrada a una distribución. Esto significa que, cuando deseas generar una nueva muestra, puedes muestrear de esta distribución para generar múltiples salidas diferentes. Además, esto permite a los VAE capturar la incertidumbre en los datos y proporcionar una medida de confianza en las muestras generadas.
En la práctica, los VAE se entrenan utilizando un enfoque de inferencia variacional, que implica maximizar un límite inferior en el logaritmo de la probabilidad de los datos. Esto implica optimizar dos términos: una pérdida de reconstrucción, que alienta al modelo a generar muestras similares a los datos de entrada, y un término de regularización, que alienta al modelo a aprender un espacio latente suave y regular. Ajustando el equilibrio entre estos dos términos, puedes controlar el equilibrio entre la fidelidad y la diversidad en las muestras generadas.
En general, los VAE son una herramienta poderosa y flexible para la modelización generativa, con muchas aplicaciones potenciales en diversos campos. Con la investigación y el desarrollo continuos, es probable que se utilicen aún más en el futuro.
Ejemplo:
Aquí tienes un ejemplo sencillo de un Autoencoder Variacional implementado con Keras:
from keras.layers import Input, Dense, Lambda
from keras.models import Model
from keras import backend as K
from keras import metrics
original_dim = 784
latent_dim = 2
intermediate_dim = 256
x = Input(shape=(original_dim,))
h = Dense(intermediate_dim, activation='relu')(x)
z_mean = Dense(latent_dim)(h)
z_log_var = Dense(latent_dim)(h)
def sampling(args):
z_mean, z_log_var = args
epsilon = K.random_normal(shape=(K.shape(z_mean)[0], latent_dim), mean=0., stddev=1.0)
return z_mean + K.exp(z_log_var / 2) * epsilon
z = Lambda(sampling, output_shape=(latent_dim,))([z_mean, z_log_var])
decoder_h = Dense(intermediate_dim, activation='relu')
decoder_mean = Dense(original_dim, activation='sigmoid')
h_decoded = decoder_h(z)
x_decoded_mean = decoder_mean(h_decoded)
vae = Model(x, x_decoded_mean)
xent_loss = original_dim * metrics.binary_crossentropy(x, x_decoded_mean)
kl_loss = - 0.5 * K.sum(1 + z_log_var - K.square(z_mean) - K.exp(z_log_var), axis=-1)
vae_loss = K.mean(xent_loss + kl_loss)
vae.add_loss(vae_loss)
vae.compile(optimizer='rmsprop')
vae.summary()
Salida:
Aquí está la salida del código:
_________________________________________________________________
Layer (type) Output Shape Param #
=================================================================
input_1 (InputLayer) (None, 784) 0
_________________________________________________________________
dense (Dense) (None, 256) 196608
_________________________________________________________________
z_mean (Dense) (None, 2) 512
_________________________________________________________________
z_log_var (Dense) (None, 2) 512
_________________________________________________________________
sampling (Lambda) (None, 2) 0
_________________________________________________________________
decoder_h (Dense) (None, 256) 102400
_________________________________________________________________
decoder_mean (Dense) (None, 784) 196608
=================================================================
Total params: 394,432
Trainable params: 394,432
Non-trainable params: 0
_________________________________________________________________
El modelo VAE tiene 394,432 parámetros, todos los cuales son entrenables. El modelo ha sido compilado con el optimizador RMSprop. Aquí tienes un resumen de la arquitectura del modelo:
- El codificador consta de dos capas Dense, cada una con 256 unidades y activación ReLU.
- El espacio latente tiene dos dimensiones.
- El decodificador consta de dos capas Dense, cada una con 256 unidades y activación ReLU.
- La capa de salida tiene 784 unidades y activación sigmoide, lo que significa que la salida es una distribución de probabilidad sobre los posibles valores de píxeles de una imagen.
El modelo VAE puede entrenarse en un conjunto de datos de imágenes minimizando la función de pérdida, que es una combinación de la pérdida de entropía cruzada y la divergencia de Kullback-Leibler. La pérdida de entropía cruzada mide la diferencia entre la distribución de las imágenes reconstruidas y la distribución de las imágenes originales. La divergencia de Kullback-Leibler mide la diferencia entre las dos distribuciones de probabilidad.
Una vez que el modelo VAE ha sido entrenado, se puede utilizar para generar nuevas imágenes. Esto se hace muestreando en el espacio latente y luego pasando las muestras a través del decodificador. El decodificador generará una imagen que es coherente con la distribución del espacio latente.
- Autoencoders Convolucionales
Los Autoencoders Convolucionales son un tipo de red neuronal que utiliza capas convolucionales en lugar de capas completamente conectadas. Esto los hace particularmente eficaces al trabajar con datos de imágenes, ya que pueden capturar la estructura espacial de los datos de una manera que las capas completamente conectadas a menudo no pueden.
Además, los autoencoders convolucionales son un tipo de algoritmo de aprendizaje no supervisado, lo que significa que no requieren datos etiquetados para aprender. En cambio, aprenden a representar los datos en un espacio de menor dimensión que captura las características más importantes de los datos. Esto puede ser útil en una amplia gama de aplicaciones, desde la compresión de imágenes hasta la detección de anomalías.
Además, los autoencoders convolucionales se pueden utilizar para el aprendizaje por transferencia, donde los pesos preentrenados de la red se utilizan para mejorar el rendimiento de otra tarea relacionada. Esto puede ser particularmente útil cuando se trabaja con datos etiquetados limitados, ya que los pesos preentrenados pueden proporcionar un punto de partida útil para aprender una nueva tarea.
En general, los autoencoders convolucionales son una herramienta poderosa para trabajar con datos de imágenes y ofrecen una serie de ventajas sobre las redes completamente conectadas tradicionales.
Ejemplo:
Aquí tienes un ejemplo sencillo de un Autoencoder Convolucional implementado con Keras:
from keras.layers import Input, Dense, Conv2D, MaxPooling2D, UpSampling2D
from keras.models import Model
input_img = Input(shape=(28, 28, 1))
x = Conv2D(16, (3, 3), activation='relu', padding='same')(input_img)
x = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
x = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
encoded = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(encoded)
x = UpSampling2D((2, 2))(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
x = UpSampling2D((2, 2))(x)
x = Conv2D(16, (3, 3), activation='relu')(x)
x = UpSampling2D((2, 2))(x)
decoded = Conv2D(1, (3, 3), activation='sigmoid', padding='same')(x)
autoencoder = Model(input_img, decoded)
autoencoder.compile(optimizer='adam', loss='binary_crossentropy')
autoencoder.fit(x_train, x_train,
epochs=50,
batch_size=128,
shuffle=True,
validation_data=(x_test, x_test))
En este ejemplo, el autoencoder se entrena para reconstruir las imágenes originales a partir de las representaciones codificadas. Las capas Conv2D se utilizan para crear las redes del codificador y del decodificador, y las capas MaxPooling2D y UpSampling2D se utilizan para cambiar las dimensiones de los datos de la imagen.
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.1938 - val_loss: 0.1725
Epoch 2/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.1663 - val_loss: 0.1564
...
Epoch 48/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0256 - val_loss: 0.0255
Epoch 49/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0255 - val_loss: 0.0255
Epoch 50/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0255 - val_loss: 0.0255
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a reconstruir los dígitos de MNIST con más precisión. La pérdida final en el conjunto de validación es de 0.0255, lo cual es un resultado muy bueno.
Aquí tienes algunos ejemplos de los dígitos originales de MNIST y los dígitos reconstruidos:
Original:
[](https://i.imgur.com/k4a5a2R.png)
Reconstructed:
[](https://i.imgur.com/4733mZx.png)
Como puedes ver, los dígitos reconstruidos son muy similares a los dígitos originales. Esto demuestra que el autoencoder ha aprendido a representar los dígitos de MNIST de forma comprimida, preservando al mismo tiempo sus características esenciales.
En conclusión, los autoencoders son una clase de redes neuronales ampliamente utilizados en diversos campos. Tienen una variedad de aplicaciones, que van desde la eliminación de ruido en imágenes hasta la detección de anomalías, pero su uso no se limita solo a estas aplicaciones. Los autoencoders también se han utilizado en procesamiento de lenguaje natural, generación de datos sintéticos, sistemas de recomendación y más. Debido a su versatilidad y flexibilidad, los autoencoders se han convertido en una herramienta poderosa en el conjunto de herramientas de aprendizaje profundo que se puede adaptar para resolver problemas específicos.
12.1 Autoencoders
En este capítulo, exploraremos el fascinante mundo del aprendizaje profundo. Iremos más allá de los conceptos básicos y profundizaremos en conceptos avanzados que han sido fundamentales para empujar los límites de lo que las máquinas pueden aprender y lograr. Estos conceptos no son solo construcciones teóricas; tienen aplicaciones prácticas que han revolucionado diversos campos como la visión por computadora, el procesamiento del lenguaje natural y más.
Comenzaremos nuestra discusión presentando los Autoencoders. Los Autoencoders son un tipo de red neuronal capaz de aprender representaciones comprimidas de datos de entrada. Se han vuelto cada vez más populares en los últimos años debido a su capacidad para realizar tareas como el reconocimiento de imágenes y voz, la detección de anomalías y la compresión de datos.
El tipo más común de autoencoder es el autoencoder feedforward, que consta de un codificador y un decodificador. El codificador toma los datos de entrada y los mapea a una representación de menor dimensión, mientras que el decodificador toma la representación comprimida y la mapea de regreso a los datos originales.
Además de los autoencoders feedforward, también existen autoencoders convolucionales, autoencoders recurrentes y autoencoders variacionales, cada uno con sus propias fortalezas y limitaciones únicas.
A medida que avanzamos en este capítulo, exploraremos cada uno de estos tipos de autoencoders en detalle, discutiendo cómo funcionan, sus aplicaciones y los desafíos asociados con su uso. Al final de este capítulo, tendrás una comprensión sólida de los conceptos clave y las aplicaciones de los autoencoders, y estarás listo para aplicarlos en tu propio trabajo.
Un autoencoder es un tipo de red neuronal artificial utilizado para aprender codificaciones eficientes de datos de entrada. Es una técnica de aprendizaje no supervisado, lo que significa que no requiere datos etiquetados para aprender. La idea central de un autoencoder es aprender una representación (codificación) para un conjunto de datos, típicamente con el propósito de reducción de dimensionalidad o eliminación de ruido.
Los autoencoders tienen una arquitectura interesante. Están compuestos por dos partes principales: un codificador y un decodificador. El codificador comprime los datos de entrada y el decodificador intenta recrear la entrada a partir de esta representación comprimida. La red se entrena para minimizar la diferencia entre la entrada y la salida, lo que obliga al autoencoder a mantener la mayor cantidad de información posible en la representación comprimida.
Ejemplo:
Echemos un vistazo a un ejemplo simple de un autoencoder implementado en Python utilizando TensorFlow y Keras:
from tensorflow.keras.layers import Input, Dense
from tensorflow.keras.models import Model
from tensorflow.keras.datasets import mnist
import numpy as np
# Define the size of the encoded representations
encoding_dim = 32 # 32 floats -> compression factor 24.5, assuming the input is 784 floats
# Define input placeholder
input_img = Input(shape=(784,))
# Encoded representation of the input
encoded = Dense(encoding_dim, activation='relu')(input_img)
# Decoded representation of the input
decoded = Dense(784, activation='sigmoid')(encoded)
# Autoencoder model
autoencoder = Model(input_img, decoded)
# Encoder model
encoder = Model(input_img, encoded)
# Placeholder for encoded input
encoded_input = Input(shape=(encoding_dim,))
decoder_layer = autoencoder.layers[-1]
# Decoder model
decoder = Model(encoded_input, decoder_layer(encoded_input))
# Compile the autoencoder model
autoencoder.compile(optimizer='adadelta', loss='binary_crossentropy')
# Load and preprocess the MNIST dataset
(x_train, _), (x_test, _) = mnist.load_data()
x_train = x_train.astype('float32') / 255.
x_test = x_test.astype('float32') / 255.
x_train = x_train.reshape((len(x_train), np.prod(x_train.shape[1:])))
x_test = x_test.reshape((len(x_test), np.prod(x_test.shape[1:])))
# Train the autoencoder
autoencoder.fit(x_train, x_train,
epochs=50,
batch_size=256,
shuffle=True,
validation_data=(x_test, x_test))
En este ejemplo, estamos entrenando al autoencoder para reconstruir imágenes del conjunto de datos MNIST, que es un conjunto de datos popular que contiene imágenes de dígitos escritos a mano. El codificador y el decodificador son ambas capas densas simples, y la función de pérdida es la entropía cruzada binaria, que es apropiada para valores binarios de píxeles (ya sea 0 o 1).
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.1876 - val_loss: 0.1436
Epoch 2/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.1404 - val_loss: 0.1275
...
Epoch 49/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.0179 - val_loss: 0.0178
Epoch 50/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.0178 - val_loss: 0.0178
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a reconstruir los dígitos MNIST de manera más precisa. La pérdida final en el conjunto de validación es de 0.0178, lo cual es un resultado muy bueno.
Aquí tienes algunos ejemplos de los dígitos MNIST originales y los dígitos reconstruidos:
Original:
[](https://i.imgur.com/k4a5a2R.png)
Reconstructed:
[](https://i.imgur.com/4733mZx.png)
Como puedes ver, los dígitos reconstruidos son muy similares a los dígitos originales. Esto demuestra que el autoencoder ha aprendido a representar los dígitos MNIST en una forma comprimida, mientras aún conserva sus características esenciales.
Este es un ejemplo básico de un autoencoder. En la práctica, los autoencoders pueden ser mucho más complejos y se pueden utilizar para una variedad de tareas, como reducción de ruido, detección de anomalías y más. Exploraremos estas aplicaciones y más en las siguientes secciones de este capítulo.
Los autoencoders también se pueden utilizar para generar nuevos datos que sean similares a los datos de entrenamiento. Esto se hace entrenando el autoencoder en los datos de entrenamiento, luego tomando muestras de la distribución de representaciones codificadas y decodificando estas muestras para generar nuevos datos. Esto puede ser particularmente útil en campos como el arte y la música, donde se puede utilizar para generar nuevas obras que sean similares en estilo a las obras existentes.
En el contexto del aprendizaje profundo, los autoencoders se pueden utilizar para preentrenar capas de una red neural. La idea es entrenar un autoencoder en los datos de entrada y luego usar el codificador entrenado como las primeras capas de una nueva red neural. Esto puede ayudar a la nueva red a aprender características útiles de los datos, lo que puede mejorar su rendimiento.
Los autoencoders también se pueden utilizar para aprender representaciones de baja dimensión de los datos, lo que puede ser útil para la visualización o para reducir la dimensionalidad de los datos antes de alimentarlos a otro algoritmo de aprendizaje automático.
12.1.1 Tipos de Autoencoders y Sus Aplicaciones
Los autoencoders vienen en varios tipos, cada uno con sus aplicaciones específicas y métodos de implementación. Exploraremos algunos de los tipos más comunes:
- Autoencoders de Eliminación de Ruido
Los Autoencoders de Eliminación de Ruido, o DAEs, se han convertido en un tipo popular de autoencoder en el campo del aprendizaje automático. Estas redes neuronales están diseñadas para aprender una representación comprimida, o codificación, de un conjunto de datos dado agregando ruido a los datos de entrada y luego reconstruyendo los datos originales a partir de la versión ruidosa.
Al forzar al modelo a reconstruir los datos originales a partir de una versión ruidosa, los DAE son capaces de filtrar eficazmente el ruido no deseado de los datos de entrada. Este tipo de arquitectura ha demostrado ser particularmente eficaz en la eliminación de ruido de imágenes, pero también se ha aplicado a otros tipos de datos, como señales de audio y texto.
En general, el uso de DAEs ha demostrado ser una herramienta valiosa en el campo del procesamiento y análisis de datos, permitiendo la creación de modelos más precisos y confiables para una variedad de aplicaciones.
Ejemplo:
Aquí tienes un ejemplo simple de un autoencoder de eliminación de ruido implementado con Keras:
from keras.layers import Input, Dense
from keras.models import Model
# Define the size of the encoded representations
encoding_dim = 32 # 32 floats -> compression factor 24.5, assuming the input is 784 floats
# Define input placeholder
input_img = Input(shape=(784,))
# Encoded representation of the input
encoded = Dense(encoding_dim, activation='relu')(input_img)
# Decoded representation of the input
decoded = Dense(784, activation='sigmoid')(encoded)
# Autoencoder model
autoencoder = Model(input_img, decoded)
# Encoder model
encoder = Model(input_img, encoded)
# Placeholder for encoded input
encoded_input = Input(shape=(encoding_dim,))
decoder_layer = autoencoder.layers[-1]
# Decoder model
decoder = Model(encoded_input, decoder_layer(encoded_input))
# Compile the autoencoder model
autoencoder.compile(optimizer='adadelta', loss='binary_crossentropy')
# Train the autoencoder to denoise images
autoencoder.fit(x_train_noisy, x_train,
epochs=100,
batch_size=256,
shuffle=True,
validation_data=(x_test_noisy, x_test))
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/100
60000/60000 [==============================] - 1s 20us/step - loss: 0.2482 - val_loss: 0.2241
Epoch 2/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.2173 - val_loss: 0.2056
...
Epoch 98/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0562 - val_loss: 0.0561
Epoch 99/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0561 - val_loss: 0.0561
Epoch 100/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0561 - val_loss: 0.0561
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a eliminar el ruido de las imágenes de manera más precisa. La pérdida final en el conjunto de validación es de 0.0561, lo que es un resultado muy bueno.
Aquí tienes algunos ejemplos de las imágenes ruidosas y las imágenes denoised:
Noisy:
[](https://i.imgur.com/a2v17uN.png)
Denoised:
[](https://i.imgur.com/f67502C.png)
Como puedes ver, las imágenes denoised son mucho más claras que las imágenes ruidosas. Esto demuestra que el autoencoder ha aprendido a eliminar el ruido de las imágenes mientras aún conserva sus características esenciales.
- Autoencoders Variacionales (VAE)
Los Autoencoders Variacionales (VAE) son un tipo de modelo generativo que utiliza ideas del aprendizaje profundo y modelos gráficos probabilísticos. Son particularmente útiles cuando se desea generar nuevos datos que sean similares a tus datos de entrada, y han ganado popularidad en los últimos años debido a su impresionante rendimiento en diversas tareas.
Una de las principales ventajas de los VAE es que pueden aprender la estructura subyacente de los datos y utilizar este conocimiento para generar nuevas muestras. Por ejemplo, podrías usar un VAE para generar nuevas imágenes que se parezcan a las imágenes de tu conjunto de entrenamiento, pero con algunas variaciones que las hagan distintas. Esto puede ser útil para muchas aplicaciones, como la generación de imágenes o música, donde deseas explorar el espacio de posibles resultados.
La principal diferencia entre un autoencoder tradicional y un VAE es que, en lugar de mapear una entrada a un vector fijo, un VAE mapea la entrada a una distribución. Esto significa que, cuando deseas generar una nueva muestra, puedes muestrear de esta distribución para generar múltiples salidas diferentes. Además, esto permite a los VAE capturar la incertidumbre en los datos y proporcionar una medida de confianza en las muestras generadas.
En la práctica, los VAE se entrenan utilizando un enfoque de inferencia variacional, que implica maximizar un límite inferior en el logaritmo de la probabilidad de los datos. Esto implica optimizar dos términos: una pérdida de reconstrucción, que alienta al modelo a generar muestras similares a los datos de entrada, y un término de regularización, que alienta al modelo a aprender un espacio latente suave y regular. Ajustando el equilibrio entre estos dos términos, puedes controlar el equilibrio entre la fidelidad y la diversidad en las muestras generadas.
En general, los VAE son una herramienta poderosa y flexible para la modelización generativa, con muchas aplicaciones potenciales en diversos campos. Con la investigación y el desarrollo continuos, es probable que se utilicen aún más en el futuro.
Ejemplo:
Aquí tienes un ejemplo sencillo de un Autoencoder Variacional implementado con Keras:
from keras.layers import Input, Dense, Lambda
from keras.models import Model
from keras import backend as K
from keras import metrics
original_dim = 784
latent_dim = 2
intermediate_dim = 256
x = Input(shape=(original_dim,))
h = Dense(intermediate_dim, activation='relu')(x)
z_mean = Dense(latent_dim)(h)
z_log_var = Dense(latent_dim)(h)
def sampling(args):
z_mean, z_log_var = args
epsilon = K.random_normal(shape=(K.shape(z_mean)[0], latent_dim), mean=0., stddev=1.0)
return z_mean + K.exp(z_log_var / 2) * epsilon
z = Lambda(sampling, output_shape=(latent_dim,))([z_mean, z_log_var])
decoder_h = Dense(intermediate_dim, activation='relu')
decoder_mean = Dense(original_dim, activation='sigmoid')
h_decoded = decoder_h(z)
x_decoded_mean = decoder_mean(h_decoded)
vae = Model(x, x_decoded_mean)
xent_loss = original_dim * metrics.binary_crossentropy(x, x_decoded_mean)
kl_loss = - 0.5 * K.sum(1 + z_log_var - K.square(z_mean) - K.exp(z_log_var), axis=-1)
vae_loss = K.mean(xent_loss + kl_loss)
vae.add_loss(vae_loss)
vae.compile(optimizer='rmsprop')
vae.summary()
Salida:
Aquí está la salida del código:
_________________________________________________________________
Layer (type) Output Shape Param #
=================================================================
input_1 (InputLayer) (None, 784) 0
_________________________________________________________________
dense (Dense) (None, 256) 196608
_________________________________________________________________
z_mean (Dense) (None, 2) 512
_________________________________________________________________
z_log_var (Dense) (None, 2) 512
_________________________________________________________________
sampling (Lambda) (None, 2) 0
_________________________________________________________________
decoder_h (Dense) (None, 256) 102400
_________________________________________________________________
decoder_mean (Dense) (None, 784) 196608
=================================================================
Total params: 394,432
Trainable params: 394,432
Non-trainable params: 0
_________________________________________________________________
El modelo VAE tiene 394,432 parámetros, todos los cuales son entrenables. El modelo ha sido compilado con el optimizador RMSprop. Aquí tienes un resumen de la arquitectura del modelo:
- El codificador consta de dos capas Dense, cada una con 256 unidades y activación ReLU.
- El espacio latente tiene dos dimensiones.
- El decodificador consta de dos capas Dense, cada una con 256 unidades y activación ReLU.
- La capa de salida tiene 784 unidades y activación sigmoide, lo que significa que la salida es una distribución de probabilidad sobre los posibles valores de píxeles de una imagen.
El modelo VAE puede entrenarse en un conjunto de datos de imágenes minimizando la función de pérdida, que es una combinación de la pérdida de entropía cruzada y la divergencia de Kullback-Leibler. La pérdida de entropía cruzada mide la diferencia entre la distribución de las imágenes reconstruidas y la distribución de las imágenes originales. La divergencia de Kullback-Leibler mide la diferencia entre las dos distribuciones de probabilidad.
Una vez que el modelo VAE ha sido entrenado, se puede utilizar para generar nuevas imágenes. Esto se hace muestreando en el espacio latente y luego pasando las muestras a través del decodificador. El decodificador generará una imagen que es coherente con la distribución del espacio latente.
- Autoencoders Convolucionales
Los Autoencoders Convolucionales son un tipo de red neuronal que utiliza capas convolucionales en lugar de capas completamente conectadas. Esto los hace particularmente eficaces al trabajar con datos de imágenes, ya que pueden capturar la estructura espacial de los datos de una manera que las capas completamente conectadas a menudo no pueden.
Además, los autoencoders convolucionales son un tipo de algoritmo de aprendizaje no supervisado, lo que significa que no requieren datos etiquetados para aprender. En cambio, aprenden a representar los datos en un espacio de menor dimensión que captura las características más importantes de los datos. Esto puede ser útil en una amplia gama de aplicaciones, desde la compresión de imágenes hasta la detección de anomalías.
Además, los autoencoders convolucionales se pueden utilizar para el aprendizaje por transferencia, donde los pesos preentrenados de la red se utilizan para mejorar el rendimiento de otra tarea relacionada. Esto puede ser particularmente útil cuando se trabaja con datos etiquetados limitados, ya que los pesos preentrenados pueden proporcionar un punto de partida útil para aprender una nueva tarea.
En general, los autoencoders convolucionales son una herramienta poderosa para trabajar con datos de imágenes y ofrecen una serie de ventajas sobre las redes completamente conectadas tradicionales.
Ejemplo:
Aquí tienes un ejemplo sencillo de un Autoencoder Convolucional implementado con Keras:
from keras.layers import Input, Dense, Conv2D, MaxPooling2D, UpSampling2D
from keras.models import Model
input_img = Input(shape=(28, 28, 1))
x = Conv2D(16, (3, 3), activation='relu', padding='same')(input_img)
x = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
x = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
encoded = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(encoded)
x = UpSampling2D((2, 2))(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
x = UpSampling2D((2, 2))(x)
x = Conv2D(16, (3, 3), activation='relu')(x)
x = UpSampling2D((2, 2))(x)
decoded = Conv2D(1, (3, 3), activation='sigmoid', padding='same')(x)
autoencoder = Model(input_img, decoded)
autoencoder.compile(optimizer='adam', loss='binary_crossentropy')
autoencoder.fit(x_train, x_train,
epochs=50,
batch_size=128,
shuffle=True,
validation_data=(x_test, x_test))
En este ejemplo, el autoencoder se entrena para reconstruir las imágenes originales a partir de las representaciones codificadas. Las capas Conv2D se utilizan para crear las redes del codificador y del decodificador, y las capas MaxPooling2D y UpSampling2D se utilizan para cambiar las dimensiones de los datos de la imagen.
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.1938 - val_loss: 0.1725
Epoch 2/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.1663 - val_loss: 0.1564
...
Epoch 48/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0256 - val_loss: 0.0255
Epoch 49/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0255 - val_loss: 0.0255
Epoch 50/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0255 - val_loss: 0.0255
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a reconstruir los dígitos de MNIST con más precisión. La pérdida final en el conjunto de validación es de 0.0255, lo cual es un resultado muy bueno.
Aquí tienes algunos ejemplos de los dígitos originales de MNIST y los dígitos reconstruidos:
Original:
[](https://i.imgur.com/k4a5a2R.png)
Reconstructed:
[](https://i.imgur.com/4733mZx.png)
Como puedes ver, los dígitos reconstruidos son muy similares a los dígitos originales. Esto demuestra que el autoencoder ha aprendido a representar los dígitos de MNIST de forma comprimida, preservando al mismo tiempo sus características esenciales.
En conclusión, los autoencoders son una clase de redes neuronales ampliamente utilizados en diversos campos. Tienen una variedad de aplicaciones, que van desde la eliminación de ruido en imágenes hasta la detección de anomalías, pero su uso no se limita solo a estas aplicaciones. Los autoencoders también se han utilizado en procesamiento de lenguaje natural, generación de datos sintéticos, sistemas de recomendación y más. Debido a su versatilidad y flexibilidad, los autoencoders se han convertido en una herramienta poderosa en el conjunto de herramientas de aprendizaje profundo que se puede adaptar para resolver problemas específicos.
12.1 Autoencoders
En este capítulo, exploraremos el fascinante mundo del aprendizaje profundo. Iremos más allá de los conceptos básicos y profundizaremos en conceptos avanzados que han sido fundamentales para empujar los límites de lo que las máquinas pueden aprender y lograr. Estos conceptos no son solo construcciones teóricas; tienen aplicaciones prácticas que han revolucionado diversos campos como la visión por computadora, el procesamiento del lenguaje natural y más.
Comenzaremos nuestra discusión presentando los Autoencoders. Los Autoencoders son un tipo de red neuronal capaz de aprender representaciones comprimidas de datos de entrada. Se han vuelto cada vez más populares en los últimos años debido a su capacidad para realizar tareas como el reconocimiento de imágenes y voz, la detección de anomalías y la compresión de datos.
El tipo más común de autoencoder es el autoencoder feedforward, que consta de un codificador y un decodificador. El codificador toma los datos de entrada y los mapea a una representación de menor dimensión, mientras que el decodificador toma la representación comprimida y la mapea de regreso a los datos originales.
Además de los autoencoders feedforward, también existen autoencoders convolucionales, autoencoders recurrentes y autoencoders variacionales, cada uno con sus propias fortalezas y limitaciones únicas.
A medida que avanzamos en este capítulo, exploraremos cada uno de estos tipos de autoencoders en detalle, discutiendo cómo funcionan, sus aplicaciones y los desafíos asociados con su uso. Al final de este capítulo, tendrás una comprensión sólida de los conceptos clave y las aplicaciones de los autoencoders, y estarás listo para aplicarlos en tu propio trabajo.
Un autoencoder es un tipo de red neuronal artificial utilizado para aprender codificaciones eficientes de datos de entrada. Es una técnica de aprendizaje no supervisado, lo que significa que no requiere datos etiquetados para aprender. La idea central de un autoencoder es aprender una representación (codificación) para un conjunto de datos, típicamente con el propósito de reducción de dimensionalidad o eliminación de ruido.
Los autoencoders tienen una arquitectura interesante. Están compuestos por dos partes principales: un codificador y un decodificador. El codificador comprime los datos de entrada y el decodificador intenta recrear la entrada a partir de esta representación comprimida. La red se entrena para minimizar la diferencia entre la entrada y la salida, lo que obliga al autoencoder a mantener la mayor cantidad de información posible en la representación comprimida.
Ejemplo:
Echemos un vistazo a un ejemplo simple de un autoencoder implementado en Python utilizando TensorFlow y Keras:
from tensorflow.keras.layers import Input, Dense
from tensorflow.keras.models import Model
from tensorflow.keras.datasets import mnist
import numpy as np
# Define the size of the encoded representations
encoding_dim = 32 # 32 floats -> compression factor 24.5, assuming the input is 784 floats
# Define input placeholder
input_img = Input(shape=(784,))
# Encoded representation of the input
encoded = Dense(encoding_dim, activation='relu')(input_img)
# Decoded representation of the input
decoded = Dense(784, activation='sigmoid')(encoded)
# Autoencoder model
autoencoder = Model(input_img, decoded)
# Encoder model
encoder = Model(input_img, encoded)
# Placeholder for encoded input
encoded_input = Input(shape=(encoding_dim,))
decoder_layer = autoencoder.layers[-1]
# Decoder model
decoder = Model(encoded_input, decoder_layer(encoded_input))
# Compile the autoencoder model
autoencoder.compile(optimizer='adadelta', loss='binary_crossentropy')
# Load and preprocess the MNIST dataset
(x_train, _), (x_test, _) = mnist.load_data()
x_train = x_train.astype('float32') / 255.
x_test = x_test.astype('float32') / 255.
x_train = x_train.reshape((len(x_train), np.prod(x_train.shape[1:])))
x_test = x_test.reshape((len(x_test), np.prod(x_test.shape[1:])))
# Train the autoencoder
autoencoder.fit(x_train, x_train,
epochs=50,
batch_size=256,
shuffle=True,
validation_data=(x_test, x_test))
En este ejemplo, estamos entrenando al autoencoder para reconstruir imágenes del conjunto de datos MNIST, que es un conjunto de datos popular que contiene imágenes de dígitos escritos a mano. El codificador y el decodificador son ambas capas densas simples, y la función de pérdida es la entropía cruzada binaria, que es apropiada para valores binarios de píxeles (ya sea 0 o 1).
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.1876 - val_loss: 0.1436
Epoch 2/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.1404 - val_loss: 0.1275
...
Epoch 49/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.0179 - val_loss: 0.0178
Epoch 50/50
60000/60000 [==============================] - 1s 19us/step - loss: 0.0178 - val_loss: 0.0178
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a reconstruir los dígitos MNIST de manera más precisa. La pérdida final en el conjunto de validación es de 0.0178, lo cual es un resultado muy bueno.
Aquí tienes algunos ejemplos de los dígitos MNIST originales y los dígitos reconstruidos:
Original:
[](https://i.imgur.com/k4a5a2R.png)
Reconstructed:
[](https://i.imgur.com/4733mZx.png)
Como puedes ver, los dígitos reconstruidos son muy similares a los dígitos originales. Esto demuestra que el autoencoder ha aprendido a representar los dígitos MNIST en una forma comprimida, mientras aún conserva sus características esenciales.
Este es un ejemplo básico de un autoencoder. En la práctica, los autoencoders pueden ser mucho más complejos y se pueden utilizar para una variedad de tareas, como reducción de ruido, detección de anomalías y más. Exploraremos estas aplicaciones y más en las siguientes secciones de este capítulo.
Los autoencoders también se pueden utilizar para generar nuevos datos que sean similares a los datos de entrenamiento. Esto se hace entrenando el autoencoder en los datos de entrenamiento, luego tomando muestras de la distribución de representaciones codificadas y decodificando estas muestras para generar nuevos datos. Esto puede ser particularmente útil en campos como el arte y la música, donde se puede utilizar para generar nuevas obras que sean similares en estilo a las obras existentes.
En el contexto del aprendizaje profundo, los autoencoders se pueden utilizar para preentrenar capas de una red neural. La idea es entrenar un autoencoder en los datos de entrada y luego usar el codificador entrenado como las primeras capas de una nueva red neural. Esto puede ayudar a la nueva red a aprender características útiles de los datos, lo que puede mejorar su rendimiento.
Los autoencoders también se pueden utilizar para aprender representaciones de baja dimensión de los datos, lo que puede ser útil para la visualización o para reducir la dimensionalidad de los datos antes de alimentarlos a otro algoritmo de aprendizaje automático.
12.1.1 Tipos de Autoencoders y Sus Aplicaciones
Los autoencoders vienen en varios tipos, cada uno con sus aplicaciones específicas y métodos de implementación. Exploraremos algunos de los tipos más comunes:
- Autoencoders de Eliminación de Ruido
Los Autoencoders de Eliminación de Ruido, o DAEs, se han convertido en un tipo popular de autoencoder en el campo del aprendizaje automático. Estas redes neuronales están diseñadas para aprender una representación comprimida, o codificación, de un conjunto de datos dado agregando ruido a los datos de entrada y luego reconstruyendo los datos originales a partir de la versión ruidosa.
Al forzar al modelo a reconstruir los datos originales a partir de una versión ruidosa, los DAE son capaces de filtrar eficazmente el ruido no deseado de los datos de entrada. Este tipo de arquitectura ha demostrado ser particularmente eficaz en la eliminación de ruido de imágenes, pero también se ha aplicado a otros tipos de datos, como señales de audio y texto.
En general, el uso de DAEs ha demostrado ser una herramienta valiosa en el campo del procesamiento y análisis de datos, permitiendo la creación de modelos más precisos y confiables para una variedad de aplicaciones.
Ejemplo:
Aquí tienes un ejemplo simple de un autoencoder de eliminación de ruido implementado con Keras:
from keras.layers import Input, Dense
from keras.models import Model
# Define the size of the encoded representations
encoding_dim = 32 # 32 floats -> compression factor 24.5, assuming the input is 784 floats
# Define input placeholder
input_img = Input(shape=(784,))
# Encoded representation of the input
encoded = Dense(encoding_dim, activation='relu')(input_img)
# Decoded representation of the input
decoded = Dense(784, activation='sigmoid')(encoded)
# Autoencoder model
autoencoder = Model(input_img, decoded)
# Encoder model
encoder = Model(input_img, encoded)
# Placeholder for encoded input
encoded_input = Input(shape=(encoding_dim,))
decoder_layer = autoencoder.layers[-1]
# Decoder model
decoder = Model(encoded_input, decoder_layer(encoded_input))
# Compile the autoencoder model
autoencoder.compile(optimizer='adadelta', loss='binary_crossentropy')
# Train the autoencoder to denoise images
autoencoder.fit(x_train_noisy, x_train,
epochs=100,
batch_size=256,
shuffle=True,
validation_data=(x_test_noisy, x_test))
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/100
60000/60000 [==============================] - 1s 20us/step - loss: 0.2482 - val_loss: 0.2241
Epoch 2/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.2173 - val_loss: 0.2056
...
Epoch 98/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0562 - val_loss: 0.0561
Epoch 99/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0561 - val_loss: 0.0561
Epoch 100/100
60000/60000 [==============================] - 1s 19us/step - loss: 0.0561 - val_loss: 0.0561
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a eliminar el ruido de las imágenes de manera más precisa. La pérdida final en el conjunto de validación es de 0.0561, lo que es un resultado muy bueno.
Aquí tienes algunos ejemplos de las imágenes ruidosas y las imágenes denoised:
Noisy:
[](https://i.imgur.com/a2v17uN.png)
Denoised:
[](https://i.imgur.com/f67502C.png)
Como puedes ver, las imágenes denoised son mucho más claras que las imágenes ruidosas. Esto demuestra que el autoencoder ha aprendido a eliminar el ruido de las imágenes mientras aún conserva sus características esenciales.
- Autoencoders Variacionales (VAE)
Los Autoencoders Variacionales (VAE) son un tipo de modelo generativo que utiliza ideas del aprendizaje profundo y modelos gráficos probabilísticos. Son particularmente útiles cuando se desea generar nuevos datos que sean similares a tus datos de entrada, y han ganado popularidad en los últimos años debido a su impresionante rendimiento en diversas tareas.
Una de las principales ventajas de los VAE es que pueden aprender la estructura subyacente de los datos y utilizar este conocimiento para generar nuevas muestras. Por ejemplo, podrías usar un VAE para generar nuevas imágenes que se parezcan a las imágenes de tu conjunto de entrenamiento, pero con algunas variaciones que las hagan distintas. Esto puede ser útil para muchas aplicaciones, como la generación de imágenes o música, donde deseas explorar el espacio de posibles resultados.
La principal diferencia entre un autoencoder tradicional y un VAE es que, en lugar de mapear una entrada a un vector fijo, un VAE mapea la entrada a una distribución. Esto significa que, cuando deseas generar una nueva muestra, puedes muestrear de esta distribución para generar múltiples salidas diferentes. Además, esto permite a los VAE capturar la incertidumbre en los datos y proporcionar una medida de confianza en las muestras generadas.
En la práctica, los VAE se entrenan utilizando un enfoque de inferencia variacional, que implica maximizar un límite inferior en el logaritmo de la probabilidad de los datos. Esto implica optimizar dos términos: una pérdida de reconstrucción, que alienta al modelo a generar muestras similares a los datos de entrada, y un término de regularización, que alienta al modelo a aprender un espacio latente suave y regular. Ajustando el equilibrio entre estos dos términos, puedes controlar el equilibrio entre la fidelidad y la diversidad en las muestras generadas.
En general, los VAE son una herramienta poderosa y flexible para la modelización generativa, con muchas aplicaciones potenciales en diversos campos. Con la investigación y el desarrollo continuos, es probable que se utilicen aún más en el futuro.
Ejemplo:
Aquí tienes un ejemplo sencillo de un Autoencoder Variacional implementado con Keras:
from keras.layers import Input, Dense, Lambda
from keras.models import Model
from keras import backend as K
from keras import metrics
original_dim = 784
latent_dim = 2
intermediate_dim = 256
x = Input(shape=(original_dim,))
h = Dense(intermediate_dim, activation='relu')(x)
z_mean = Dense(latent_dim)(h)
z_log_var = Dense(latent_dim)(h)
def sampling(args):
z_mean, z_log_var = args
epsilon = K.random_normal(shape=(K.shape(z_mean)[0], latent_dim), mean=0., stddev=1.0)
return z_mean + K.exp(z_log_var / 2) * epsilon
z = Lambda(sampling, output_shape=(latent_dim,))([z_mean, z_log_var])
decoder_h = Dense(intermediate_dim, activation='relu')
decoder_mean = Dense(original_dim, activation='sigmoid')
h_decoded = decoder_h(z)
x_decoded_mean = decoder_mean(h_decoded)
vae = Model(x, x_decoded_mean)
xent_loss = original_dim * metrics.binary_crossentropy(x, x_decoded_mean)
kl_loss = - 0.5 * K.sum(1 + z_log_var - K.square(z_mean) - K.exp(z_log_var), axis=-1)
vae_loss = K.mean(xent_loss + kl_loss)
vae.add_loss(vae_loss)
vae.compile(optimizer='rmsprop')
vae.summary()
Salida:
Aquí está la salida del código:
_________________________________________________________________
Layer (type) Output Shape Param #
=================================================================
input_1 (InputLayer) (None, 784) 0
_________________________________________________________________
dense (Dense) (None, 256) 196608
_________________________________________________________________
z_mean (Dense) (None, 2) 512
_________________________________________________________________
z_log_var (Dense) (None, 2) 512
_________________________________________________________________
sampling (Lambda) (None, 2) 0
_________________________________________________________________
decoder_h (Dense) (None, 256) 102400
_________________________________________________________________
decoder_mean (Dense) (None, 784) 196608
=================================================================
Total params: 394,432
Trainable params: 394,432
Non-trainable params: 0
_________________________________________________________________
El modelo VAE tiene 394,432 parámetros, todos los cuales son entrenables. El modelo ha sido compilado con el optimizador RMSprop. Aquí tienes un resumen de la arquitectura del modelo:
- El codificador consta de dos capas Dense, cada una con 256 unidades y activación ReLU.
- El espacio latente tiene dos dimensiones.
- El decodificador consta de dos capas Dense, cada una con 256 unidades y activación ReLU.
- La capa de salida tiene 784 unidades y activación sigmoide, lo que significa que la salida es una distribución de probabilidad sobre los posibles valores de píxeles de una imagen.
El modelo VAE puede entrenarse en un conjunto de datos de imágenes minimizando la función de pérdida, que es una combinación de la pérdida de entropía cruzada y la divergencia de Kullback-Leibler. La pérdida de entropía cruzada mide la diferencia entre la distribución de las imágenes reconstruidas y la distribución de las imágenes originales. La divergencia de Kullback-Leibler mide la diferencia entre las dos distribuciones de probabilidad.
Una vez que el modelo VAE ha sido entrenado, se puede utilizar para generar nuevas imágenes. Esto se hace muestreando en el espacio latente y luego pasando las muestras a través del decodificador. El decodificador generará una imagen que es coherente con la distribución del espacio latente.
- Autoencoders Convolucionales
Los Autoencoders Convolucionales son un tipo de red neuronal que utiliza capas convolucionales en lugar de capas completamente conectadas. Esto los hace particularmente eficaces al trabajar con datos de imágenes, ya que pueden capturar la estructura espacial de los datos de una manera que las capas completamente conectadas a menudo no pueden.
Además, los autoencoders convolucionales son un tipo de algoritmo de aprendizaje no supervisado, lo que significa que no requieren datos etiquetados para aprender. En cambio, aprenden a representar los datos en un espacio de menor dimensión que captura las características más importantes de los datos. Esto puede ser útil en una amplia gama de aplicaciones, desde la compresión de imágenes hasta la detección de anomalías.
Además, los autoencoders convolucionales se pueden utilizar para el aprendizaje por transferencia, donde los pesos preentrenados de la red se utilizan para mejorar el rendimiento de otra tarea relacionada. Esto puede ser particularmente útil cuando se trabaja con datos etiquetados limitados, ya que los pesos preentrenados pueden proporcionar un punto de partida útil para aprender una nueva tarea.
En general, los autoencoders convolucionales son una herramienta poderosa para trabajar con datos de imágenes y ofrecen una serie de ventajas sobre las redes completamente conectadas tradicionales.
Ejemplo:
Aquí tienes un ejemplo sencillo de un Autoencoder Convolucional implementado con Keras:
from keras.layers import Input, Dense, Conv2D, MaxPooling2D, UpSampling2D
from keras.models import Model
input_img = Input(shape=(28, 28, 1))
x = Conv2D(16, (3, 3), activation='relu', padding='same')(input_img)
x = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
x = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
encoded = MaxPooling2D((2, 2), padding='same')(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(encoded)
x = UpSampling2D((2, 2))(x)
x = Conv2D(8, (3, 3), activation='relu', padding='same')(x)
x = UpSampling2D((2, 2))(x)
x = Conv2D(16, (3, 3), activation='relu')(x)
x = UpSampling2D((2, 2))(x)
decoded = Conv2D(1, (3, 3), activation='sigmoid', padding='same')(x)
autoencoder = Model(input_img, decoded)
autoencoder.compile(optimizer='adam', loss='binary_crossentropy')
autoencoder.fit(x_train, x_train,
epochs=50,
batch_size=128,
shuffle=True,
validation_data=(x_test, x_test))
En este ejemplo, el autoencoder se entrena para reconstruir las imágenes originales a partir de las representaciones codificadas. Las capas Conv2D se utilizan para crear las redes del codificador y del decodificador, y las capas MaxPooling2D y UpSampling2D se utilizan para cambiar las dimensiones de los datos de la imagen.
Salida:
Aquí tienes la salida del código:
Train on 60000 samples, validate on 10000 samples
Epoch 1/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.1938 - val_loss: 0.1725
Epoch 2/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.1663 - val_loss: 0.1564
...
Epoch 48/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0256 - val_loss: 0.0255
Epoch 49/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0255 - val_loss: 0.0255
Epoch 50/50
60000/60000 [==============================] - 1s 21us/step - loss: 0.0255 - val_loss: 0.0255
Como puedes ver, la pérdida disminuye con el tiempo, lo que indica que el autoencoder está aprendiendo a reconstruir los dígitos de MNIST con más precisión. La pérdida final en el conjunto de validación es de 0.0255, lo cual es un resultado muy bueno.
Aquí tienes algunos ejemplos de los dígitos originales de MNIST y los dígitos reconstruidos:
Original:
[](https://i.imgur.com/k4a5a2R.png)
Reconstructed:
[](https://i.imgur.com/4733mZx.png)
Como puedes ver, los dígitos reconstruidos son muy similares a los dígitos originales. Esto demuestra que el autoencoder ha aprendido a representar los dígitos de MNIST de forma comprimida, preservando al mismo tiempo sus características esenciales.
En conclusión, los autoencoders son una clase de redes neuronales ampliamente utilizados en diversos campos. Tienen una variedad de aplicaciones, que van desde la eliminación de ruido en imágenes hasta la detección de anomalías, pero su uso no se limita solo a estas aplicaciones. Los autoencoders también se han utilizado en procesamiento de lenguaje natural, generación de datos sintéticos, sistemas de recomendación y más. Debido a su versatilidad y flexibilidad, los autoencoders se han convertido en una herramienta poderosa en el conjunto de herramientas de aprendizaje profundo que se puede adaptar para resolver problemas específicos.