← Flutter & Dart

Fundamentos de Dart

¿Qué hacen el operador cascada (`..`), el spread (`...`) y los operadores de colección (`if`/`for` dentro de listas) en Dart?

Ver respuesta — intenta responderla en voz alta primero

El operador cascada .. permite llamar varios métodos sobre el mismo objeto sin repetir su nombre. El spread ... inserta todos los elementos de una colección dentro de otra. Los collection if y collection for dejan construir listas con lógica condicional o bucles directamente dentro de los corchetes.

  • Cascada (..): en vez de escribir el objeto una y otra vez, encadenas operaciones sobre él. Cada .. opera sobre el objeto original (no sobre lo que devuelve el método). Muy usado al configurar objetos.
  • Spread (...): "desparrama" los elementos de una colección dentro de otra. ...otraLista mete todos sus elementos. Existe la versión null-aware ...? que no falla si la colección es null.
  • Collection if / for: puedes meter un if o un for dentro de la definición de una lista para incluir elementos condicionalmente o generarlos en bucle. Se usa muchísimo en Flutter para armar listas de widgets.
class Perro {
  String nombre = "";
  int edad = 0;
  void ladrar() => print("$nombre dice guau");
}

void main() {
  // Cascada: configuro el mismo objeto sin repetirlo
  final perro = Perro()
    ..nombre = "Rex"
    ..edad = 3
    ..ladrar(); // "Rex dice guau"
  print("${perro.nombre}, ${perro.edad}"); // "Rex, 3"

  // Spread: insertar elementos de otra lista
  final base = [1, 2, 3];
  final ampliada = [0, ...base, 4];
  print(ampliada); // [0, 1, 2, 3, 4]

  // Spread null-aware
  List<int>? talVezNull;
  final segura = [0, ...?talVezNull, 5];
  print(segura); // [0, 5]

  // Collection if / for
  bool mostrarExtra = true;
  final items = [
    "a",
    for (var i = 0; i < 3; i++) "item$i",
    if (mostrarExtra) "extra",
  ];
  print(items); // [a, item0, item1, item2, extra]
}

Confundir la cascada .. con el acceso normal .. Con .., la expresión completa devuelve el objeto original, no el resultado del método. Si haces final x = lista..add(1);, x es la lista, no el resultado de add. Si por error usaras . esperando encadenar, obtendrías el valor de retorno del método, que suele ser void o algo distinto.

"La cascada .. me deja configurar o llamar varios métodos sobre el mismo objeto sin repetir su nombre, y siempre devuelve el objeto original. El spread ... inserta los elementos de una colección dentro de otra, y tiene la variante ...? que ignora un valor null. Y los collection if y collection for me permiten construir listas con condicionales y bucles directo entre los corchetes, algo que uso mucho en Flutter para armar listas de widgets condicionalmente."

Reto rápido

¿Qué imprime este código?

final a = [1, 2];
final b = [...a, if (a.length > 1) 99];
print(b);
Ver respuesta

Imprime [1, 2, 99]. El spread ...a mete 1 y 2. Luego el collection if evalúa a.length > 1, que es true (la longitud es 2), así que agrega el 99.