resina - ¿Qué es una incrustación en Keras?
incrustaciones onlay (5)
La documentación de Keras no es clara en realidad. Entiendo que podemos usar esto para comprimir el espacio de la característica de entrada en uno más pequeño. Pero, ¿cómo se hace esto desde una perspectiva de diseño neural? ¿Es un autoenocder, RBM?
En Keras, la capa de
Embedding
NO
es una simple capa de multiplicación matricial, sino una capa de tabla de consulta (consulte la función de llamada a continuación o la
Embedding
original).
def call(self, inputs):
if K.dtype(inputs) != ''int32'':
inputs = K.cast(inputs, ''int32'')
out = K.gather(self.embeddings, inputs)
return out
Lo que hace es mapear cada uno de los enteros conocidos
n
en las
inputs
a un vector de entidad entrenable
W[n]
, cuya dimensión es la llamada longitud de entidad incrustada.
En palabras simples (desde el punto de vista de la funcionalidad), es un codificador único y una capa totalmente conectada . Los pesos de las capas son entrenables.
Hasta donde sé, la capa de incrustación es una simple multiplicación de matriz que transforma las palabras en sus incrustaciones de palabras correspondientes.
Los pesos de la capa de incrustación son de la forma (vocabulario_tamaño, incrustación_dimensión). Para cada muestra de entrenamiento, su entrada son enteros, que representan ciertas palabras. Los enteros están en el rango del tamaño del vocabulario. La capa de incrustación transforma cada número entero i en la línea i-ésima de la matriz de pesos de incrustación.
Para hacer esto rápidamente como una multiplicación matricial, los enteros de entrada no se almacenan como una lista de enteros sino como una matriz de un solo hot. Por lo tanto, la forma de entrada es (nb_words, vocabulary_size) con un valor distinto de cero por línea. Si multiplica esto por los pesos de incrustación, obtendrá la salida en la forma
(nb_words, vocab_size) x (vocab_size, embedding_dim) = (nb_words, embedding_dim)
Entonces, con una simple multiplicación matricial, transforma todas las palabras de una muestra en las incrustaciones de palabras correspondientes.
La
capa de
Embedding
Keras
no realiza ninguna multiplicación de matriz, sino que solo:
1. crea una matriz de peso de dimensiones (vocabulario_tamaño) x (incrustación_dimensión)
2. indexa esta matriz de peso
Siempre es útil echar un vistazo al código fuente para comprender lo que hace una clase.
En este caso, veremos la
class
Embedding
que hereda de la
class
capa base llamada
Layer
.
(1) - Crear una matriz de peso de dimensiones (vocabulario_tamaño) x (incrustación_dimensión) :
Esto ocurre en la función de
build
de
Embedding
:
def build(self, input_shape):
self.embeddings = self.add_weight(
shape=(self.input_dim, self.output_dim),
initializer=self.embeddings_initializer,
name=''embeddings'',
regularizer=self.embeddings_regularizer,
constraint=self.embeddings_constraint,
dtype=self.dtype)
self.built = True
Si echa un vistazo a la
Layer
clase base, verá que la función
add_weight
anterior simplemente crea una matriz de pesos entrenables (en este caso de dimensiones
(vocabulario_tamaño) x (
dimensión_de_incrustación)):
def add_weight(self,
name,
shape,
dtype=None,
initializer=None,
regularizer=None,
trainable=True,
constraint=None):
"""Adds a weight variable to the layer.
# Arguments
name: String, the name for the weight variable.
shape: The shape tuple of the weight.
dtype: The dtype of the weight.
initializer: An Initializer instance (callable).
regularizer: An optional Regularizer instance.
trainable: A boolean, whether the weight should
be trained via backprop or not (assuming
that the layer itself is also trainable).
constraint: An optional Constraint instance.
# Returns
The created weight variable.
"""
initializer = initializers.get(initializer)
if dtype is None:
dtype = K.floatx()
weight = K.variable(initializer(shape),
dtype=dtype,
name=name,
constraint=constraint)
if regularizer is not None:
with K.name_scope(''weight_regularizer''):
self.add_loss(regularizer(weight))
if trainable:
self._trainable_weights.append(weight)
else:
self._non_trainable_weights.append(weight)
return weight
(2) - Indexación de esta matriz de peso
Esto ocurre en la función de
call
de
Embedding
:
def call(self, inputs):
if K.dtype(inputs) != ''int32'':
inputs = K.cast(inputs, ''int32'')
out = K.gather(self.embeddings, inputs)
return out
Esta función devuelve el resultado de la capa de
Embedding
que es
K.gather(self.embeddings, inputs)
.
Lo que
tf.keras.backend.gather
hace exactamente es indexar las matrices de
self.embeddings
matriz de pesos (ver la función de
build
anterior) de acuerdo con las
inputs
que deberían ser listas de enteros positivos.
Estas listas se pueden recuperar, por ejemplo, si pasa sus entradas de texto / palabras a la función one_hot de Keras que codifica un texto en una lista de índices de palabras de tamaño n (esta NO es una codificación activa; consulte también este ejemplo para obtener más información: https://machinelearningmastery.com/use-word-embedding-layers-deep-learning-keras/ ).
Por lo tanto, eso es todo. No hay multiplicación de matrices.
Por el contrario,
la capa de
Embedding
Keras
solo es útil porque exactamente evita realizar una multiplicación de matriz
y, por lo tanto, economiza en algunos recursos computacionales.
De lo contrario, podría usar una capa
Keras
Dense
(después de haber codificado sus datos de entrada) para obtener una matriz de pesos entrenables (de
(vocabulario_tamaño) x (
dimensiones de
incrustación)
) y luego simplemente hacer la multiplicación para obtener la salida que será exactamente lo mismo con la salida de la capa de
Embedding
.
Para comprender mejor cualquier función, es un buen hábito mirar el código fuente. Aquí está para Embedding así que básicamente es una tabla de búsqueda entrenable.