Anunciando Dart 2.2: Código nativo más rápido, soporte para set literals

Hoy anunciamos el lanzamiento estable del SDK de Dart 2.2, una actualización incremental de Dart 2 que ofrece rendimiento mejorado de…

Hoy anunciamos la versión estable del SDK de Dart 2.2, una actualización incremental de Dart 2 que ofrece mejor rendimiento del código nativo compilado ahead-of-time (AOT) y una nueva característica del lenguaje de literales set.

Banner de la versión Dart 2.2 destacando el rendimiento mejorado de AOT y el soporte del lenguaje de literales set.

Mejoras de rendimiento de Dart para desarrolladores de Flutter

#

Continuamos nuestro trabajo para hacer que el código compilado con AOT, como las apps de Flutter, sea aún más rápido. En Dart 2.1, reducimos la sobrecarga de las verificaciones de tipo, reduciendo enormemente el costo de las verificaciones de tipo tanto para el código compilado con AOT como para el código ejecutado en la VM con compilación JIT (just-in-time).

En Dart 2.2, nos hemos enfocado específicamente en el rendimiento del código compilado con AOT, mejorando el rendimiento de AOT en un 11–16% en microbenchmarks (a costa de un aumento de ~1% en el tamaño del código). Esta mejora es el resultado de varios trimestres de trabajo para reducir la sobrecarga de las llamadas estáticas. Nuestro código AOT optimizado ahora puede llamar al destino directamente usando una llamada relativa al PC (es decir, usando el contador de programa); antes teníamos que hacer varias búsquedas en un pool de objetos para determinar la dirección de destino. Estas optimizaciones son especialmente útiles cuando el código contiene muchas llamadas a constructores y métodos estáticos, como el código de interfaz de usuario de Flutter que crea muchos widgets.

Característica del lenguaje de literales set en Dart 2.2

#

La librería core de Dart (dart:core) contiene varias clases de colecciones para modelar Maps, Lists y Sets de objetos. Los Maps son colecciones de pares clave-valor. Las Lists son secuencias ordenadas de valores, donde cada valor puede ser accedido por un índice, y puede aparecer más de una vez. Los Sets son colecciones no ordenadas de valores, donde cada valor puede aparecer solo una vez, y donde puedes verificar eficientemente si un valor está en el set.

Las colecciones de Dart se inicializan comúnmente con constantes en tiempo de compilación, por lo que Dart tiene una sintaxis literal conveniente para expresar esta inicialización. En Dart, una List se puede inicializar con:

dart
const List<String> releases = ['Dart 2.0', 'Dart 2.1', 'Dart 2.2'];

Anteriormente, Dart soportaba la sintaxis literal solo para Lists y Maps, por lo que la inicialización de Sets era engorrosa ya que teníamos que inicializar a través de una lista:

dart
Set<String> currencies = Set.of(['EUR', 'USD', 'JPY']);

Este código no solo es incómodo e ineficiente; la falta de soporte literal impide que currencies sea una constante en tiempo de compilación. Con la extensión de literales de Dart 2.2 para soportar sets, podemos inicializar un set y hacerlo const usando una nueva sintaxis conveniente:

dart
const Set<String> currencies = {'EUR', 'USD', 'JPY'};

Para ejemplos reales de cómo el equipo de Flutter está empezando a aplicar literales set, consulta el PR #27811. Para más detalles generales sobre cómo usar literales set, consulta el tour del lenguaje Dart 2.2 actualizado.

Construyendo nuevas características del lenguaje con el Dart 2 Common Front-End (CFE)

#

Las implementaciones del lenguaje Dart — la Dart VM usada por Flutter, el compilador dart2js y el compilador de desarrollo de Dart (dartdevc) — comparten un front end común. El Dart Common Front End, o CFE, analiza el código de Dart, realiza inferencia de tipos y traduce Dart a un lenguaje intermedio de bajo nivel que las implementaciones de back end aceptan como entrada.

La característica de literales set es un ejemplo de una construcción del lenguaje que pudimos desarrollar rápidamente gracias al CFE. El código para analizar literales set y realizar inferencia de tipos se implementó una vez en el CFE para todos los back ends de Dart. Además, construimos una implementación transicional solo de front end que podía ser usada por los back ends inicialmente. En la implementación transicional, la versión no const del literal set de currencies de arriba se tradujo durante la compilación al equivalente de:

dart
Set<String> currencies = Set<String>()..add('EUR')..add('USD')..add('JPY');

La implementación transicional de literales set const es diferente porque los sets const no se pueden construir incrementalmente por partes. En su lugar, implementamos esto en términos de una clase privada de set no modificable que envuelve un map const, donde los elementos del set son las claves del map:

dart
const Set<String> currencies =
   _UnmodifiableSet<String>({'EUR': null, 'USD': null, 'JPY': null});

La clase de set no modificable implementa los métodos de la interfaz Set en términos del map envuelto.

En general, pudimos implementar los literales set inicialmente como una característica solo del CFE. Los back ends pudieron usar la implementación del CFE inicialmente, y luego desarrollar su propio soporte nativo de manera independiente al lanzamiento inicial de la característica. Esto permitió a los backends posponer su soporte nativo hasta que los aspectos de rendimiento de esta característica se entendieran mejor.

Especificación del lenguaje Dart 2.2

#

Dart 2 fue una actualización sustancial de Dart que nos tomó un tiempo conseguir que la especificación formal del lenguaje Dart se actualizara para coincidir con todos los cambios que hicimos. Finalmente hemos completado ese trabajo, y la especificación está actualizada a partir de Dart 2.2. También hemos movido el código fuente de la especificación del lenguaje al nuevo repositorio del lenguaje, y añadido integración continua para asegurar que se genere un borrador continuo de especificación en formato PDF a medida que evolucionamos la especificación para futuras versiones del lenguaje Dart. Tanto la especificación 2.2 como la continua de Dart 2.x están disponibles en la página de especificaciones de Dart.

Obteniendo Dart 2.2

#

El SDK de Dart 2.2 está disponible desde la página principal de Dart hoy. Si eres un desarrollador de Flutter, Dart 2.2 ya está incluido. (Nota: los canales master y dev actuales de Flutter reportarán Dart 2.2. El lanzamiento estable de Flutter 1.2 de hoy reportará Dart 2.1.2; este tiene las mismas características que Dart 2.2).

Eso es todo por ahora. ¡Esperamos que disfrutes Dart 2.2!

Más de Dart