1. Programación Ciencia de datos de datos grandes Uso de inteligencia artificial para el análisis de sentimientos

Por John Paul Mueller, Luca Mueller

El análisis de sentimientos deriva computacionalmente de un texto escrito utilizando la actitud del escritor (ya sea positiva, negativa o neutral) hacia el tema del texto. Este tipo de análisis resulta útil para las personas que trabajan en marketing y comunicación porque les ayuda a comprender qué piensan los clientes y consumidores de un producto o servicio y, por lo tanto, a actuar de manera adecuada (por ejemplo, tratando de recuperar clientes insatisfechos o decidiendo utilizar una estrategia de ventas diferente ) Todos realizan análisis de sentimientos. Por ejemplo, al leer el texto, las personas intentan determinar el sentimiento que conmovió a la persona que lo escribió. Sin embargo, cuando la cantidad de textos para leer y comprender es demasiado grande y el texto se acumula constantemente, como en las redes sociales y los correos electrónicos de los clientes, es importante automatizar el análisis de sentimientos.

Análisis de sentimientos de IA

El próximo ejemplo es una prueba de RNNs usando Keras y TensorFlow que construye un algoritmo de análisis de sentimientos capaz de clasificar las actitudes expresadas en una crítica cinematográfica. Los datos son una muestra del conjunto de datos de IMDb que contiene 50,000 críticas (divididas a la mitad entre el tren y los sets de prueba) de películas acompañadas de una etiqueta que expresa el sentimiento de la crítica (0 = negativo, 1 = positivo). IMDb es una gran base de datos en línea que contiene información sobre películas, series de televisión y videojuegos. Originalmente mantenido por una base de fanáticos, ahora está a cargo de una subsidiaria de Amazon. En IMDb, las personas encuentran la información que necesitan sobre su programa favorito y publican sus comentarios o escriben una reseña para que otros visitantes la lean.

Keras ofrece un contenedor descargable para datos de IMDb. Prepara, baraja y organiza estos datos en un tren y un conjunto de prueba. En particular, los datos textuales de IMDb ofrecidos por Keras se limpian de puntuación, se normalizan en minúsculas y se transforman en valores numéricos. Cada palabra está codificada en un número que representa su clasificación en frecuencia. Las palabras más frecuentes tienen números bajos; Las palabras menos frecuentes tienen números más altos.

Como punto de partida, el código importa la función imdb de Keras y la usa para recuperar los datos de Internet (aproximadamente una descarga de 17.5MB). Los parámetros que usa el ejemplo abarcan solo las primeras 10,000 palabras, y Keras debería barajar los datos usando una semilla aleatoria específica. (Conocer la semilla permite reproducir la combinación aleatoria según sea necesario). La función devuelve dos conjuntos de tren y prueba, ambos hechos de secuencias de texto y el resultado del sentimiento.

de keras.datasets import imdb
top_words = 10000
((x_train, y_train),
(x_test, y_test)) = imdb.load_data (num_words = top_words,
semilla = 21)

Una vez que se completa el código anterior, puede verificar la cantidad de ejemplos con el siguiente código:

print ("Ejemplos de entrenamiento:% i"% len (x_train))
print ("Ejemplos de prueba:% i"% len (x_test))

Después de preguntar sobre el número de casos disponibles para su uso en la fase de entrenamiento y prueba de la red neuronal, el código genera una respuesta de 25,000 ejemplos para cada fase. (Este conjunto de datos es relativamente pequeño para un problema de idioma; claramente el conjunto de datos es principalmente para fines de demostración). Además, el código determina si el conjunto de datos está equilibrado, lo que significa que tiene un número casi igual de ejemplos de sentimientos positivos y negativos.

importar numpy como np
print (np.unique (y_train, return_counts = True))

El resultado, matriz ([12500, 12500]), confirma que el conjunto de datos se divide en partes iguales entre resultados positivos y negativos. Tal equilibrio entre las clases de respuesta se debe exclusivamente a la naturaleza demostrativa del conjunto de datos. En el mundo real, rara vez se encuentran conjuntos de datos equilibrados. El siguiente paso crea algunos diccionarios de Python que pueden convertir entre el código utilizado en el conjunto de datos y las palabras reales. De hecho, el conjunto de datos utilizado en este ejemplo está preprocesado y proporciona secuencias de números que representan las palabras, no las palabras en sí. (Los algoritmos LSTM y GRU que encuentra en Keras esperan secuencias de números como números).

word_to_id = {w: i ​​+ 3 para w, i en imdb.get_word_index (). items ()}
id_to_word = {0: '', 1: '', 2': ''}
id_to_word.update ({i + 3: w para w, i en imdb.get_word_index (). items ()})
def convert_to_text (secuencia):
return '' .join ([id_to_word [s] para s en secuencia si s> = 3])
print (convert_to_text (x_train [8]))

El fragmento de código anterior define dos diccionarios de conversión (de palabras a códigos numéricos y viceversa) y una función que traduce los ejemplos del conjunto de datos en texto legible. Como ejemplo, el código imprime el noveno ejemplo: "esta película fue como un mal choque de trenes tan horrible como lo fue ...". A partir de este extracto, puede anticipar fácilmente que el sentimiento de esta película no es positivo. Palabras como malo, ruina y horrible transmiten un fuerte sentimiento negativo, y eso hace que adivinar el sentimiento correcto sea fácil.

En este ejemplo, recibe las secuencias numéricas y las convierte de nuevo en palabras, pero lo contrario es común. Por lo general, obtienes frases compuestas de palabras y las conviertes en secuencias de enteros para alimentar a una capa de RNN. Keras ofrece una función especializada, Tokenizer, que puede hacer eso por usted. Utiliza los métodos fit_on_text, para aprender a mapear palabras a enteros a partir de datos de entrenamiento, y messages_to_matrix, para transformar el texto en una secuencia.

Sin embargo, en otras frases, es posible que no encuentre palabras tan reveladoras para el análisis de sentimientos. El sentimiento se expresa de una manera más sutil o indirecta, y la comprensión del sentimiento al principio del texto puede no ser posible porque las frases y palabras reveladoras pueden aparecer mucho más tarde en el discurso. Por esta razón, también debe decidir qué parte de la frase desea analizar.

Convencionalmente, toma una parte inicial del texto y la usa como representante de toda la revisión. A veces solo necesitas unas pocas palabras iniciales, por ejemplo las primeras 50 palabras, para tener sentido; a veces necesitas más. Los textos especialmente largos no revelan su orientación temprana. Por lo tanto, depende de usted comprender el tipo de texto con el que está trabajando y decidir cuántas palabras analizar con el aprendizaje profundo. Este ejemplo considera solo las primeras 200 palabras, que deberían ser suficientes.

Ha notado que el código comienza a dar código a las palabras que comienzan con el número 3, dejando así códigos del 0 al 2. Los números más bajos se usan para etiquetas especiales, como la señalización del comienzo de la frase, llenando espacios vacíos para arreglar la secuencia. con cierta longitud y marcando las palabras que están excluidas porque no son lo suficientemente frecuentes. Este ejemplo recoge solo las 10,000 palabras más frecuentes. El uso de etiquetas para señalar el comienzo, el final y las situaciones notables es un truco que funciona con los RNN, especialmente para la traducción automática.

de keras.preprocessing.sequence import pad_sequences
max_pad = 200
x_train = pad_sequences (x_train,
maxlen = max_pad)
x_test = pad_sequences (x_test,
maxlen = max_pad)
print (x_train [0])

Al usar la función pad_sequences de Keras con max_pad configurado en 200, el código toma las primeras doscientas palabras de cada revisión. En caso de que la revisión contenga menos de doscientas palabras, tantos valores cero como sea necesario preceden a la secuencia para alcanzar el número requerido de elementos de secuencia. Cortar las secuencias a una cierta longitud y llenar los vacíos con valores cero se denomina relleno de entrada, una actividad de procesamiento importante cuando se usan RNN como algoritmos de aprendizaje profundo. Ahora el código diseña la arquitectura:

de keras.models import Sequential
from keras.layers import Bidirectional, Dense, Dropout
de keras.layers importan GlobalMaxPool1D, LSTM
from keras.layers.embeddings import Embedded
embedding_vector_length = 32
modelo = secuencial ()
model.add (incrustación (top_words,
embedded_vector_length,
input_length = max_pad))
model.add (Bidireccional (LSTM (64, return_sequences = True)))
model.add (GlobalMaxPool1D ())
model.add (Denso (16, activación = "relu"))
model.add (Denso (1, activación = "sigmoide"))
model.compile (loss = 'binary_crossentropy',
optimizador = 'adam',
métricas = ['precisión'])
print (model.summary ())

El fragmento de código anterior define la forma del modelo de aprendizaje profundo, donde utiliza algunas capas especializadas para el procesamiento del lenguaje natural de Keras. El ejemplo también ha requerido un resumen del modelo (comando model.summary ()) para determinar qué está sucediendo con la arquitectura mediante el uso de diferentes capas neurales.

Tiene la capa de incrustación, que transforma las secuencias numéricas en una incrustación de palabras densas. Ese tipo de inclusión de palabras es más adecuado para ser aprendido por una capa de RNN. Keras proporciona una capa de incrustación que, además de ser necesariamente la primera capa de la red, puede realizar dos tareas:

  • Aplicar incrustaciones de palabras preentrenadas (como Word2vec o GloVe) a la secuencia de entrada. Solo necesita pasar la matriz que contiene la incrustación a sus pesos de parámetros. Crear una palabra incrustada desde cero, en función de las entradas que recibe.

En este segundo caso, la incrustación solo necesita saber:

  • input_dim: el tamaño del vocabulario esperado de los datos output_dim: el tamaño del espacio de incrustación que se producirá (las llamadas dimensiones) input_length: el tamaño de secuencia que se espera

Después de determinar los parámetros, Embedded encontrará los mejores pesos para transformar las secuencias en una matriz densa durante el entrenamiento. El tamaño de la matriz densa viene dado por la longitud de las secuencias y la dimensionalidad de la incrustación.

Si utiliza la capa de incrustación proporcionada por Keras, debe recordar que la función proporciona solo una matriz de peso del tamaño del vocabulario por la dimensión de la incrustación deseada. Asigna las palabras a las columnas de la matriz y luego ajusta los pesos de la matriz a los ejemplos proporcionados. Esta solución, aunque práctica para problemas de lenguaje no estándar, no es análoga a las incrustaciones de palabras discutidas anteriormente, que se entrenan de una manera diferente y en millones de ejemplos.

El ejemplo utiliza envoltura bidireccional: una capa LSTM de 64 celdas. Bidireccional transforma una capa LSTM normal al duplicarla: en el primer lado, aplica la secuencia normal de entradas que proporciona; en el segundo, pasa el reverso de la secuencia. Usas este enfoque porque a veces usas palabras en un orden diferente o diferente y construir una capa bidireccional capturará cualquier patrón de palabras, sin importar el orden. La implementación de Keras es sencilla: simplemente la aplica como una función en la capa que desea renderizar bidireccionalmente.

El LSTM bidireccional está configurado para devolver secuencias (return_sequences = True); es decir, para cada celda, devuelve el resultado proporcionado después de ver cada elemento de la secuencia. Los resultados, para cada secuencia, son una matriz de salida de 200 x 128, donde 200 es el número de elementos de secuencia y 128 es el número de celdas LSTM utilizadas en la capa. Esta técnica evita que el RNN tome el último resultado de cada celda LSTM. Las sugerencias sobre el sentimiento del texto podrían aparecer en cualquier parte de la secuencia de palabras incrustadas.

En resumen, es importante no tomar el último resultado de cada celda, sino el mejor resultado. Por lo tanto, el código se basa en la siguiente capa, GlobalMaxPool1D, para verificar cada secuencia de resultados proporcionada por cada celda LSTM y retener solo el resultado máximo. Eso debería garantizar que el ejemplo elija la señal más fuerte de cada celda LSTM, que es de esperar que se especialice en su entrenamiento para elegir algunas señales significativas.

Después de filtrar las señales neuronales, el ejemplo tiene una capa de 128 salidas, una para cada celda LSTM. El código reduce y mezcla las señales utilizando una capa densa sucesiva de 16 neuronas con activación ReLU (haciendo que solo pasen señales positivas). La arquitectura termina con un nodo final que utiliza la activación sigmoidea, que exprimirá los resultados en el rango 0-1 y los hará ver como probabilidades.

Una vez definida la arquitectura, ahora puede entrenar a la red para realizar análisis de sentimientos. Serán suficientes tres épocas (pasar los datos tres veces a través de la red para que aprenda los patrones). El código utiliza lotes de 256 revisiones cada vez, lo que permite que la red vea suficiente variedad de palabras y sentimientos cada vez antes de actualizar sus pesos utilizando la propagación hacia atrás. Finalmente, el código se centra en los resultados proporcionados por los datos de validación (que no son parte de los datos de capacitación). Obtener un buen resultado de los datos de validación significa que la red neuronal está procesando la entrada correctamente. El código informa sobre los datos de validación justo después de que finaliza cada época.

history = model.fit (x_train, y_train,
validation_data = (x_test, y_test),
épocas = 3, tamaño de lote = 256)

Obtener los resultados lleva un tiempo, pero si está utilizando una GPU, se completará en el tiempo que tome tomar una taza de café. En este punto, puede evaluar los resultados, nuevamente utilizando los datos de validación. (Los resultados no deberían tener sorpresas o diferencias con respecto a lo que informó el código durante el entrenamiento).

pérdida, métrica = model.evaluate (x_test, y_test, verbose = 0)
print ("Precisión de prueba:% 0.3f"% métrica)

La precisión final, que es el porcentaje de respuestas correctas de la red neuronal profunda, será un valor de alrededor del 85-86 por ciento. El resultado cambiará ligeramente cada vez que ejecute el experimento debido a la aleatorización al construir su red neuronal. Eso es perfectamente normal dado el pequeño tamaño de los datos con los que está trabajando. Si comienza con los pesos de la suerte correctos, el aprendizaje será más fácil en una sesión de entrenamiento tan corta.

Al final, su red es un analizador de sentimientos que puede adivinar el sentimiento expresado en una crítica de película correctamente alrededor del 85 por ciento de las veces. Dada aún más datos de entrenamiento y arquitecturas neuronales más sofisticadas, puede obtener resultados que son aún más impresionantes. En marketing, se utiliza una herramienta similar para automatizar muchos procesos que requieren leer texto y tomar medidas. Una vez más, podría acoplar una red como esta con una red neuronal que escucha una voz y la convierte en texto. (Esta es otra aplicación de RNN, que ahora alimenta a Alexa, Siri, Google Voice y muchos otros asistentes personales). La transición permite que la aplicación entienda el sentimiento incluso en expresiones vocales, como una llamada telefónica de un cliente.