No hace mucho tiempo, las aplicaciones de aprendizaje automático comenzaron a florecer en varias industrias. Las empresas adaptaron rápidamente su infraestructura existente para poder enviar modelos de aprendizaje automático que generarían predicciones en lotes.

Funciona bastante bien. Ahora, parece que todo el mundo habla de cómo el aprendizaje automático en tiempo real es el futuro. ¿Pero es de verdad? ¿Realmente deberíamos hacer el esfuerzo adicional necesario para poner (y mantener) los modelos en tiempo real en producción?

¿Estás interesado en un mini mapa que te ayude a razonar sobre cuándo y cómo crear modelos de aprendizaje automático en tiempo real? ¡Sigue leyendo este artículo!

¿Qué son los modelos en tiempo real?

No existe una definición única de lo que es un modelo en tiempo real.

Cuando hablamos de modelos en tiempo real, podríamos pensar en dos procesos distintos que pueden ocurrir en tiempo real: inferencia o aprendizaje.

Lo primero que probablemente venga a la mente es que tiempo real significa aprendizaje en tiempo real, donde un modelo recibe continuamente nuevos datos de entrenamiento y actualiza sus parámetros. Esto es ciertamente emocionante, pero aún raro de encontrar en la vida real. Sin embargo, en tiempo real también significa inferencia en tiempo real, en la que un modelo entrenado puede recibir solicitudes en cualquier momento y devolver predicciones sincrónicamente. Esto se encuentra más comúnmente en la vida real.

En este artículo, presentamos estrategias para construir modelos que hagan predicciones en tiempo real.

Descubre las oportunidades

¿Por qué utilizar modelos en tiempo real?

A veces, debes usar un modelo en tiempo real simplemente porque el problema que estás abordando requiere una toma de decisiones instantánea.

Supongamos que se te pide que presentes una solución basada en Aprendizaje Automático que ayudará a escalar y mejorar el servicio al usuario. Cada vez que un usuario abre el chat en nuestra aplicación y escribe un mensaje, debemos identificar automáticamente de qué está hablando y actuar en consecuencia (por ejemplo, redirigirlo a un chat con un especialista humano).

Podríamos enmarcar este problema como un problema de clasificación de clases múltiples, en el que las clases podrían ser diferentes productos (como tarjetas de crédito, cuentas de ahorro, inversiones, etc.) y construir un clasificador que reciba el texto escrito por el usuario y devuelva el producto del que es más probable que esté hablando.

Este caso de uso requiere un modelo en tiempo real porque el modelo se alimenta de datos recién generados y también porque el usuario espera una respuesta rápida. A partir de ese caso de uso específico, podemos intentar encontrar algunas reglas generales que nos ayuden a decidir cuándo es ideal (o necesario) usar un modelo en tiempo real:

  • Experiencia de usuario mejorada. Hay varias situaciones que son similares a nuestro caso de uso, donde se espera una respuesta síncrona. También hay otros casos de uso en los que el modelo debe integrarse en un dispositivo móvil y, por lo tanto, hacer predicciones en tiempo real. Eso podría suceder, por ejemplo, si se requiere que el modelo genere predicciones incluso cuando no hay conexión a Internet.
  • Uso de datos más recientes. Los modelos por lotes hacen predicciones a partir de datos que tienen al menos unas horas de antigüedad. Los modelos en tiempo real, por otro lado, pueden hacer predicciones a partir de datos que tienen solo unos segundos de antigüedad, como el texto que el usuario acaba de escribir o su ubicación actual.
  • Conjunto de entradas desconocido (o muy grande). Los modelos por lotes hacen predicciones a partir de un conjunto predefinido de entradas. Por ejemplo, podemos tener un modelo de fraude que se ejecuta en lotes y genera una puntuación de fraude para cada usuario; en este caso, el conjunto de entradas corresponde al conjunto de usuarios. A veces no es factible saber de antemano cuáles son todas las entradas posibles. En nuestro caso de uso, el conjunto de entradas sería el conjunto de todos los textos que los usuarios pueden escribir, que en su mayoría son desconocidos.
  • Uso eficiente de los recursos. Los modelos por lotes generan predicciones para todas las entradas posibles, incluso cuando la mayoría de esas predicciones no se utilizan para la toma de decisiones. Los modelos en tiempo real, por otro lado, generan predicciones para una entrada a la vez, solo cuando se necesitan.

Bien. Hay muchas buenas razones para construir modelos en tiempo real. Ahora solo es cuestión de desplegarlos. Debería ser rápido y fácil, ¿verdad? Podríamos hacer eso en menos de 10 líneas de código:

Primer intento de servir un modelo en tiempo real

No tan rápido.

¿Cómo construir modelos en tiempo real?

Dado que es probable que las limitaciones de la infraestructura afecten las decisiones de modelado, la creación de un modelo en tiempo real requiere una colaboración muy estrecha entre el científico de datos y el ingeniero de aprendizaje automático.

Hablaremos de dos requisitos que debemos tener en cuenta desde el inicio del desarrollo de un modelo en tiempo real: canalización en tiempo real e inferencia rápida.

Canalización en tiempo real

Una canalización en tiempo real debe recopilar y preparar todas las entradas requeridas por el modelo. Los datos pueden obtenerse de diferentes fuentes:

  • Solicitar carga útil. En el escenario más simple de nuestro caso de uso, podríamos tener el texto escrito por el usuario como nuestra única entrada. Inmediatamente después de que el usuario ejecuta una acción, como escribir un mensaje y presionar el botón Enviar, los datos se agregan a una carga útil y se envían directamente al modelo a través de una solicitud.
  • Transmisión de eventos. Si queremos enriquecer nuestro modelo agregando más información sobre el comportamiento reciente del usuario, podríamos crear una función que incluya las últimas pantallas que el usuario ha visto antes de abrir el chat. Estos datos no estarían disponibles en el contexto de nuestro microservicio de modelo de chat, ni en el contexto de un entorno analítico. Debido a que son datos muy recientes, necesitaríamos obtenerlos de eventos de transmisión generados por otros microservicios.
  • Almacén de funciones (Feature store). Es posible que queramos mejorar aún más nuestro modelo agregando también información sobre el historial del usuario. Podríamos crear una función que nos diga los productos que el usuario ha usado más en los últimos 60 días más o menos. Esta función se generaría mediante la suma de datos históricos. Podría llevar mucho tiempo generarlo en tiempo real, por lo que, idealmente, se generaría previamente en lotes y, por lo tanto, lo obtendríamos de un almacén de funciones.

Después de recopilar los datos, todavía tenemos que preprocesarlos. Los datos históricos que provienen del almacén de funciones ya están preprocesados, mientras que los datos nuevos que provienen de la carga útil de la solicitud o de los eventos de transmisión están en su formato más crudo. Ahora, podemos ver claramente que tenemos dos canalizaciones separadas: una canalización por lotes y una canalización en tiempo real.

Queremos asegurarnos de que la función de preprocesamiento que se aplicó a los datos en la canalización por lotes durante el entrenamiento sea exactamente la misma función que se aplicó a los datos en la canalización en tiempo real durante la inferencia. No hacer esto se conoce como sesgo de entrenamiento-entrega.

Inferencia Rápida

¿Recuerdas esa red neuronal súper vanguardista que construiste y que logró una precisión del 99% para todas las clases? Si intentas medir su tiempo de predicción, te sorprenderás al descubrir que puede tardar muchos segundos. Aunque suene rápido, especialmente para una gran red neuronal, en realidad no lo es.

Una respuesta que se considera rápida suele tardar milisegundos. Piensa en cuánto tiempo estaría dispuesto a esperar el usuario antes de volver a intentar una acción o simplemente abandonar la aplicación.

Los modelos en tiempo real deben ser rápidos. Básicamente, hay dos formas de hacerlos más rápidos: usar hardware más potente o construir modelos más livianos.

Usar hardware más potente (como GPU) parece una solución rápida y razonable, pero podría ser más difícil de mantener a largo plazo, ya que probablemente sería una solución no estandarizada y requeriría un monitoreo más cercano. Además, el tiempo de respuesta general podría no ser lo suficientemente rápido. Si tuviéramos un modelo pesado que necesita ejecutar inferencias en la GPU, habría una sobrecarga de comunicación considerable entre la CPU y la GPU.

Por otro lado, construir modelos más livianos es más rentable y más fácil de mantener. Si utilizáramos modelos ligeros, podríamos escalar los servicios de aprendizaje automático de forma horizontal como los microservicios normales, posiblemente utilizando herramientas internas ya existentes.

Los modelos pesados se pueden comprimir usando varias técnicas, tales como:

  • Poda. Encontrar pesos redundantes en un árbol o red neuronal y establecerlos en cero, es decir, cortar algunas conexiones entre nodos en el modelo. Se basa en la suposición de que un modelo complejo contiene varios submodelos y, por lo tanto, la poda intenta encontrar un submodelo óptimo.
  • Destilación del Conocimiento. Cuando un modelo compacto aprende a imitar el comportamiento de un modelo grande. Se utiliza en el contexto de las redes neuronales. Podemos entrenar un modelo destilado desde cero o usar modelos destilados previamente entrenados que ya están disponibles en las bibliotecas. Uno de esos modelos disponibles es DistilBERT, una versión destilada de BERT que tiene solo el 60% del tamaño del modelo original.
  • Cuantización. Consiste en bajar la precisión de los números en coma flotante que representan los pesos del modelo. Normalmente se realiza después del entrenamiento, ya que intentar optimizar los pesos con valores de baja precisión puede provocar un entrenamiento inestable o incluso divergente. Como ejemplo, podemos reducir la precisión de los pesos de números de punto flotante de 32 bits a enteros de 8 bits, lo que daría como resultado un modelo que es 4 veces más pequeño.

Vale la pena señalar que la poda y la cuantización están disponibles tanto en TensorFlow como en PyTorch, por lo que debería ser rápido y fácil ejecutar experimentos que combinen diferentes técnicas.

Además de comprimir modelos, también podemos evaluar la efectividad del uso del almacenamiento en caché para almacenar algunas predicciones. En nuestro caso de uso, después de preprocesar la entrada de texto, podríamos terminar con una entrada que se repite con frecuencia. En ese caso, llamaríamos al modelo solo la primera vez que se ve esa entrada; luego, en llamadas posteriores, obtendríamos la predicción directamente del caché.

Pero… ¿es esto la vida real?

¡Seguro que lo es! La mayoría de las empresas comienzan sus viajes de aprendizaje automático experimentando con modelos por lotes, ya que se perciben como un enfoque más fácil y seguro. Sin embargo, a medida que los expertos en aprendizaje automático y las partes interesadas del negocio trabajan juntos para descubrir nuevas áreas donde el aprendizaje automático podría aplicarse para maximizar el valor, los problemas que requieren modelos en tiempo real (como el modelo de chat del que hemos hablado) surgen inevitablemente.

Miles de empresas ya están enviando modelos de aprendizaje automático en tiempo real de forma segura y escalable, incluyendo Nubank. Si tienes curiosidad acerca de lo que se puede hacer con los sistemas de aprendizaje automático en tiempo real, únete a nosotros.


Written by Ana Martinazzo
Reviewed by Felipe Almeida

Descubre las oportunidades