Conozca el neuroeditor en el navegador, o cómo enseñamos modelos LLM para ayudar a los usuarios con textos

Probablemente todo el mundo sabe lo difícil que puede resultar a veces escribir y editar textos: ya sea la dilación banal, el “problema de la pizarra en blanco” o la búsqueda de errores tipográficos según todas las reglas del idioma ruso. Y a veces simplemente necesitamos simplificar un poco el texto, para no sobrecargarlo accidentalmente con frases complejas, o más corto, para que quepa en una pequeña publicación en las redes sociales.

A principios de año, el navegador se actualizó y adquirió nuevas funciones de red neuronal. Hoy me gustaría detenerme en un neuroeditor que facilita el trabajo con texto monótono y que requiere mucho tiempo. Debajo del corte hay una historia sobre cómo mejoramos la solución anterior y finalmente se nos ocurrió la idea de una herramienta separada. También te contaré cómo procesamos el texto industrial personalizado y por qué la reescritura y la generación son tareas diferentes.

Un poco de historia

Así, en febrero de 2024, el navegador recibió una nueva función: la neuroedición. En aquel entonces solo estaba disponible en los campos de entrada de los sitios web. Hasta hoy, el usuario podía elegir entre tres opciones de procesamiento de textos: corregir errores, mejorar y acortar.

En aquel momento, los modelos que realizaban estas tareas eran los siguientes:

  • Un modelo separado fue responsable de cada acción. En el modo de corrección se requirió que el modelo corrigiera errores gramaticales en el texto; en los modos de reducción y mejora se requirió reformularlo.

  • Para cada modelo, recopilamos nuestro propio conjunto de datos de entrenamiento, que consta de 5000 textos públicos en Internet. Los textos en sí eran lo más “vivos” posible: en alguna parte había jerga, obscenidades, caracteres especiales.

  • Todos los modelos fueron entrenados adicionalmente por YandexGPT Lite utilizando un adaptador LoRa. Elegimos LoRa por el tamaño limitado del conjunto de datos y la mejor calidad que pudimos lograr.

Después del lanzamiento, nos dimos cuenta de que no hay límites para la perfección. No podíamos ignorar la compatibilidad con el idioma inglés para las tres funciones de texto. Para hacer esto, colaboramos con el equipo de Translator: ayudaron con la implementación del modelo de corrección del idioma inglés y compartieron conjuntos de datos para otros modelos. La destilación la hicimos nosotros mismos. Y todo esto, un par de semanas después del lanzamiento.

Después de esto hubo una pausa. Comenzamos a analizar el comportamiento de los usuarios y mejorar la calidad básica.

Deuda técnica: arreglar errores arreglar errores

Pero echemos un vistazo más de cerca a la calidad básica. Hay una historia interesante detrás de la función de corrección de errores en general. ¿A todo el mundo le encantan las historias sobre deuda técnica?

Entonces, durante la primera versión, no teníamos métricas fuera de línea para validar los experimentos y utilizamos la ayuda de los editores para evaluar la calidad de los modelos de corrección de errores. Al mismo tiempo, parecía que esta historia podría automatizarse fácilmente y ahorrar tiempo para validar experimentos.

Métricas sin conexión

Como punto de partida, teníamos un difalk (una herramienta que muestra la diferencia entre versiones) escrito en Go. El diffalka funciona basándose en el algoritmo de búsqueda de índice LCS (Longest Common Subsequence): es decir, buscamos las subsecuencias comunes más largas. Consideramos la diferencia detectada entre los textos como el cambio realizado por el modelo, y resaltamos en rojo lo corregido y en verde lo corregido.

Ahora a la idea: al tener tal diferencia, puedes contar la cantidad de errores que el modelo no corrige y, en base a esto, validar hipótesis sobre la calidad. Si sabemos calcular la diferencia, entonces nada nos impide calcularla entre dos textos, donde el primer texto es el resultado de una corrección del modelo y la segunda versión correcta es del editor. Se pueden especializar más errores de puntuación y ortografía. Afortunadamente, ya teníamos un conjunto de datos de prueba con pares de “texto con errores – texto sin errores”.

Como resultado, comenzamos a ahorrar tiempo, pero no renunciamos a los editores: nos ayudan a validar los modelos antes de implementarlos en producción. De esta forma podremos estar seguros de que todo funciona como debería y no se nos ha escapado nada crítico.

experimentos

Y ahora puedes experimentar un poco más con diferentes versiones de modelos y métodos de entrenamiento, que es lo que hicimos nosotros. Actualmente tenemos tres casos de éxito:

Transición de la arquitectura Decoder a Encoder-Decoder. En resumen, el modelo solía constar de un elemento principal: el decodificador. Intentó hacer dos cosas a la vez: comprender la esencia del texto con errores y corregirlos.

Cuando la arquitectura cambió, aparecieron dos elementos: un codificador y un decodificador. Cada uno tiene su propio objetivo: el codificador intenta comprender el texto fuente y lo traduce a una representación vectorial, mientras que el decodificador, basándose en la información del codificador y el texto original, genera la versión correcta. En este caso, la responsabilidad por el resultado se comparte a nivel arquitectónico, lo que ayuda a que el modelo se vuelva más inteligente con el mismo número de parámetros o modere sus apetitos y sea más rápido con la misma calidad.

Para nosotros esta transición resultó útil: gracias a ella redujimos el tiempo de generación a la mitad y no sufrimos calidad.

Aprendizaje curricular. Este es un enfoque similar a cómo aprenden las personas: gradualmente, comenzando con tareas simples y pasando a otras más complejas. Hicimos lo mismo: nos alejamos de la simple reproducción aleatoria y comenzamos a ordenar ejemplos de entrenamiento.

Al mismo tiempo, para el problema de la corrección de errores existe una forma bastante sencilla, pero no perfectamente precisa, de comprender la complejidad: la distancia de Levenshtein. Cuanto más grande es, más complejo es el ejemplo que ve el modelo frente a él. Este método de clasificación no tiene en cuenta la complejidad de los errores, pero le permite enseñarle al modelo a simplemente copiar el texto primero y luego, paso a paso, corregir más y más errores.

Paso de fase. Además, esta es una fase ligeramente diferente, que ya resulta familiar para quienes están familiarizados con el LLM. En nuestro caso, dividimos el proceso de SFT en dos partes:

  • preentrenamiento en un conjunto de datos ligeramente “sucio” pero grande;

  • capacitación adicional en un conjunto de datos más pequeño, pero muy bueno.

El conjunto de datos para el preentrenamiento también se recopiló en dos fases:

  1. Pasamos muchos textos por un modelo de corrección de errores ya preparado y obtuvimos textos de referencia.

  2. Agregamos errores artificiales: nada complicado, solo aleatoriedad y un conjunto de reglas para daños aleatorios a los textos: errores tipográficos, duplicación de letras, comas adicionales.

Para estas dos acciones, recibimos pares de textos con errores artificiales y textos de referencia, aquellos en los que el modelo corrigió la mayoría de los errores. Debido a que el modelo no es ideal, el conjunto de datos tiene una cierta proporción de errores no corregidos, pero esto se compensa con la segunda fase de entrenamiento adicional sobre datos ideales, pero pequeños.

A continuación, entrenamos un nuevo modelo, primero lo entrenamos previamente y luego lo entrenamos más con datos ideales. Así conseguimos estabilizar el comportamiento en los textos largos.

Al final: gracias a todos estos experimentos, pudimos asegurarnos de que el modelo de corrección recibiera una aceleración de ×2, y en conjuntos de datos de código abierto logramos un aumento promedio en la calidad de +10% dependiendo del dominio.

Por lo tanto, tenemos un conjunto de modelos para una gama limitada de tareas, hay soporte para varios editores de terceros y hay usuarios cuyos comentarios se pueden encontrar. Y nos dimos cuenta de que necesitamos…

editor neuro

Nos arremangamos y vamos a la gente realizó un castdev. Descubrimos que a los usuarios les gusta la neuroedición, pero hay un inconveniente: hay que buscar el punto de entrada, es decir, un campo de entrada de texto, lo que es una pérdida de tiempo.

Entonces nos dimos cuenta de que un editor separado es una continuación lógica del desarrollo de toda la función de neuroedición.

¿Por qué? En primer lugar, proporcionamos un punto de entrada constante y, en segundo lugar, la capacidad de editar el texto recibido de un modelo por otros modelos. Felicidad, ponis y bancos de gelatina.

Dato interesante: por lo general, los servicios primero se posicionan como simples editores de texto o herramientas de traducción de texto, y solo luego se agregan funciones de inteligencia artificial para simplificar el trabajo. El navegador hizo exactamente lo contrario: primero los chips de IA y luego el editor

Al mismo tiempo, sorprender al usuario con algo ya es difícil. La mayoría de las características de un editor moderno son simplemente buenos modales, como la compatibilidad con Markdown o el guardado en la nube. Por eso, nos enfocamos en la simplificación y facilidad de uso, brindando beneficios al usuario a través de LLM.

La cuestión de cómo aportar valor de esta manera es generalmente compleja. En primer lugar, no está claro qué funciones son necesarias y cuáles no serán demandadas. En segundo lugar, hacer que el editor sea fácil de usar desde el punto de vista de la interfaz de usuario tampoco es fácil: es necesario ser discreto y al mismo tiempo ofrecer acciones simples pero frecuentes con un solo botón.

¿Qué puedes hacer con el texto ahora?

Desde el principio sabíamos que queríamos posicionarnos como una herramienta. Ya sea un LLM o algo más bajo el capó, realmente no importa siempre y cuando haga el trabajo. Debido a estas entradas, llegamos a la conclusión de que el elemento principal del editor es el campo de entrada de texto, y todo lo demás es una conveniencia adicional.

Ahora pasemos a cosas más interesantes. Hemos ampliado la cantidad de acciones de los botones; todas están ocultas en el botón “Reescribir”.

Hay nueve acciones en total:

  • correcciones de errores;

  • traducción de textos;

  • mejora (se ha producido un cambio de marca y ahora se llama “Hermoso”);

  • en otras palabras;

  • corto;

  • más simple;

  • más difícil;

  • más formal;

  • en un estilo conversacional.

Seleccionamos todas estas acciones basándonos en castdevs, experimentos cuantitativos, análisis de la competencia y simplemente clasificando con nuestros instintos internos. Al mismo tiempo, entendemos que no pueden cubrir toda la variedad de variaciones en el trabajo con texto. Es por eso que agregamos la capacidad de resolver cualquier problema que pueda expresarse como instrucciones de transformación de texto.

Para recibir instrucciones y ejecutarlas es necesario formularlas en algún lugar. Para ello, apareció el campo de entrada “Ayuda con texto” o, como llamamos a esta función entre nosotros, “industrial personalizado”.

industriales personalizados

La función principal es acercar nuestro editor a las capacidades de los sistemas de diálogo, permitiéndole ir más allá de los límites de los botones “listos para usar”, pero sin privar al usuario de un estado de fluidez cuando trabaja con texto.

El editor es un producto menos estándar que los sistemas de diálogo habituales. Al trabajar con ellos, juega un papel importante el contexto en el que se basa la asistencia al usuario. Normalmente, el sistema necesita almacenar entre 5 y 10 mensajes en la memoria para procesar correctamente todas las solicitudes. En el editor, decidimos dejar el contexto como uno solo.

Además, entrenamos el modelo del editor para tareas que diferían de las básicas. Esto hizo posible inferir un modelo basado en YandexGPT 3 Light, pero al mismo tiempo no sufrir en calidad en relación con los resultados de la versión YandexGPT 3 Pro del modelo.

Pero para seguir entrenando el modelo, primero es necesario comprender qué tareas de texto resuelven los usuarios con mayor frecuencia mediante sistemas de diálogo. Lo que hicimos:

  1. Recibimos un conjunto de datos interactivo impersonal con modelos GPT y comenzamos el análisis.

  2. Seleccionamos conversaciones ordinarias de tareas realizadas mediante modelos generativos (es decir, directamente de tareas de texto).

  3. Creamos un clasificador que puede comprender cuál de las tareas con el texto está sucediendo: reescribir, agregar, generar o verificar hechos.

  4. El clasificador filtró solo las tareas de reescribir y sumar.

  5. Usando YandexGPT 3 Pro, dividimos los mensajes en diálogos en dos partes: texto procesado y texto industrial.

Un punto interesante: en la cuarta etapa, nos dimos cuenta de que las tareas de reescribir y generar están en una proporción de 1: 1, y luego comenzamos a observar exactamente cómo se pide reescribir el texto.

Para comprender el panorama general, necesitábamos analizar el flujo de bienes industriales. Sin embargo, en los registros esto no siempre es una combinación de “mensaje + texto”; la mayoría de las veces es algo separado: texto, mensaje, aclaración. A menudo estas tareas sólo pueden intercalarse con la ayuda del contexto durante el diálogo. Por eso necesitábamos la quinta etapa y la ayuda de YandexGPT 3 Pro.

Por cierto, así descubrimos que la solicitud más frecuente era una reformulación. Los usuarios pidieron simplemente reescribir el texto sin ningún detalle. Así apareció la acción “En otras palabras”.

Luego comenzamos a trabajar en un producto industrial personalizado. Al estudiar el conjunto de datos conversacionales, notamos que había muchas solicitudes para mejorar el texto y corregir errores. Esto significa que el diálogo con el modelo se ha convertido en una forma más común de comunicación con las redes neuronales. Y después de la prueba beta, llegamos a la conclusión de que el usuario espera el mismo resultado tanto después de hacer clic en el botón “Corregir” como después de la solicitud “Corregir el texto” en la línea del mensaje.

Quizás a muchas personas les resulte más fácil interactuar mediante comandos de texto que mediante soluciones de botón. Por lo tanto, lo hicimos para que, independientemente del método de solicitud (mediante un botón o un mensaje), el clasificador redirija al usuario al modelo diseñado para esta tarea.

Como resultado, se formó una arquitectura en la que hay una consulta, un clasificador y modelos que aceptan tareas. Dividimos las tareas personalizadas restantes en dos categorías: reescritura y generación. Reescribir implica cambiar la estructura del texto sin cambiar su significado, mientras que la generación agrega e inventa nuevos contenidos.

También seleccionamos tareas en las que estamos absolutamente seguros de que el modelo universal no podrá acercarse en calidad a los especializados: corrección de errores, mejora y reformulación. Entrenamos aún más al clasificador para cada uno de ellos y comenzamos a redirigir las solicitudes.

El diagrama muestra que el flujo se distribuye en cinco partes, cada una de las cuales es un modelo independiente. Se distribuyen mediante un clasificador que puede identificar siete categorías. Tres de ellos (corrección, mejora y reformulación) son los mismos modelos que están disponibles con solo hacer clic en un botón en la parte superior del editor.

Las tareas restantes (reescribir, completar, generar y verificar datos) son las categorías en las que dividimos las tareas de texto. Y si intentas visualizar la relación entre ellos, se parece a esto:

Reescritura Es una tarea en la que pides explícitamente procesar un texto de alguna manera, sin esperar que el significado del texto cambie significativamente, pero sí que cambie la estructura, el estilo o el carácter. Por ejemplo, el mensaje “Acortar el texto a un párrafo” se ajusta a esto.

Suma – una tarea que supone que desea agregar nueva información a un lugar específico en un texto existente. Por ejemplo, el mensaje “Agregar una conclusión” es adecuado.

una generación Es similar a sumar, pero su principal diferencia es que aquí el resultado contiene principalmente información nueva. Es decir, aquí nos centramos principalmente en crear texto desde cero.

Verificación de hechos es un subtipo de generación. Se diferencia en que la solicitud no se centra en contenidos creativos, sino en la obtención de información enciclopédica. Las consultas en esta categoría se parecen a esto: “¿Cuándo fue el primer vuelo al espacio?”

Clasificamos estas cuatro categorías como diferentes, pero en el esquema de ventas se combinan la reescritura y la suma, así como la generación y la verificación de hechos, según un modelo diferente para cada especialización.

Este enfoque con modelos especializados nos resulta rentable. En gran parte debido al aligeramiento de la carga: los modelos especializados son más fáciles de entrenar, son más precisos, más compactos y más rápidos, pero menos funcionales que un modelo universal grande. Al mismo tiempo, no es un problema para nosotros, si es necesario, separar el flujo de generación y verificación de datos: una generación separada con más creatividad y una verificación de hechos separada con información más precisa.

Reescritura y generación

Quizás tenga una pregunta lógica: “¿Por qué separar tareas bastante similares que normalmente se resuelven con un modelo?”

Partimos de la idea de que, a diferencia de la tarea de generación, donde la amplitud de conocimientos y un conjunto mínimo de habilidades son primordiales, la reescritura suele requerir una mayor variedad de habilidades y una pequeña amplitud de conocimientos sobre el mundo. Fue precisamente por esto (y también por el deseo de poder ajustar los modelos para nuestro dominio) que decidimos separar estas tareas.

En el caso de la reescritura, teníamos un conjunto claro de criterios que queríamos perfeccionar: afinar las habilidades, hacer que el modelo sea menos hablador y ampliar el soporte de Markdown.

Soporte de rebajas

Debajo del capó, nuestro editor envía texto etiquetado con Markdown a los modelos. Se fabricaron nuevos modelos teniendo en cuenta esta condición. Pero los modelos de neuroedición más antiguos se crearon sin este requisito.

Si ha estado utilizando la neuroedición durante mucho tiempo, es posible que haya encontrado que los modelos manejan Markdown con bastante libertad. Fácilmente podrían haber eliminado algunos de los caracteres especiales o, por el contrario, haber añadido: el comportamiento era un poco impredecible. Aprendimos sobre esto de los editores que probaron el proceso de autocorrección de errores tipográficos: simplemente usaron textos con etiquetas.

Por supuesto, este comportamiento debía corregirse. Seguimos la ruta de restauración de las marcas. Consta de tres etapas:

  1. Ejecutar texto de rebajas a través del modelo.

  2. Resurrección del marcado faltante por manos de los editores.

  3. Reentrenamiento del modelo.

Esto permitió mantener el marcado 1:1 en el modelo de corrección; en el caso de mejora y reducción, las cifras resultaron más modestas debido al tratamiento más agresivo de la estructura del texto por parte de los modelos.


El neuroeditor resultó ser uno de los neuroproyectos más grandes del navegador. Esto reúne el conocimiento y el esfuerzo de muchos equipos. Esto provocó una gran cantidad de batallas y disputas. Detrás de escena está el trabajo titánico de un gran equipo de front-end, back-end y gerentes. Esto también hizo posible ampliar el número de modelos LLM activos de la familia YandexGPT especialmente entrenados para el navegador; ahora hay más de 15.

Este proyecto fue un verdadero desafío para nosotros. Esperamos que esta actualización haga la vida de su navegador más cómoda y sencilla.

¡Escribe y reescribe!

Publicaciones Similares

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *