dartoopcascadeMenengah3 mnt baca

Cascade Notation (..)

Merangkai banyak operasi pada satu objek tanpa variabel sementara.

Panggil beruntun tanpa repetisi

Mengatur objek sering butuh banyak panggilan beruntun: cat.warna = 'merah'; cat.mesin(); cat.jalan();. Menulis nama variabel berulang-ulang itu bising. Cascade notation (..) merangkai operasi pada objek yang sama dalam satu ekspresi.

Analogi: cascade itu seperti memberi banyak instruksi ke satu orang tanpa menyebut namanya tiap kali: "Budi, pakai helm. Budi, nyalakan motor. Budi, jalan." menjadi "Budi: pakai helm, nyalakan motor, jalan."

Kenapa cascade ada?

Untuk builder pattern dan konfigurasi objek: rangkai banyak setter/pemanggilan tanpa variabel sementara. Kode terlihat seperti "resep perakitan" yang mengalir.

Bentuk dasar

dart
class Kopi {
  String jenis = '';
  bool gula = false;
  bool susu = false;

  void seduh() => print('Menyeduh $jenis...');
  void sajikan() => print('Sajikan: $jenis, gula: $gula, susu: $susu');
}

void main() {
  // Tanpa cascade: nama variabel diulang
  var k1 = Kopi();
  k1.jenis = 'tubruk';
  k1.gula = true;
  k1.seduh();

  // Dengan cascade: satu alur
  var k2 = Kopi()
    ..jenis = 'latte'
    ..gula = true
    ..susu = true
    ..seduh()
    ..sajikan();
}

.. artinya "lakukan operasi ini pada objek yang sama, lalu kembalikan objeknya (bukan hasil operasi)". Karena yang dikembalikan tetap objeknya, rantai bisa berlanjut.

Contoh kedua, cascade pada list dan objek bawaan:

dart
void main() {
  // Membangun list bertahap
  var angka = <int>[]
    ..add(1)
    ..add(2)
    ..addAll([3, 4])
    ..remove(2);
  print(angka); // [1, 3, 4]

  // StringBuffer: membangun string efisien
  var sb = StringBuffer()
    ..write('Halo, ')
    ..write('Dunia')
    ..write('!');
  print(sb.toString()); // Halo, Dunia!
}

Tanpa cascade, add mengembalikan void sehingga tidak bisa dirangkai. Cascade mengabaikan return value dan selalu meneruskan objeknya.

?.. : cascade aman-null

dart
class Mesin {
  void nyalakan() => print('Mesin nyala');
}

void main() {
  Mesin? m;
  m?..nyalakan(); // aman: tidak jalan karena m null

  m = Mesin();
  m?..nyalakan(); // Mesin nyala
}

?.. membatalkan seluruh rantai jika objeknya null. Kombinasi dengan null safety.

Kesalahan umum

1. Tertukar .. dengan .

dart
void main() {
  var sb = StringBuffer();
  // var x = sb.write('a').write('b'); // ERROR: write() return void
  sb
    ..write('a')
    ..write('b');
  print(sb); // ab
}

Satu titik (.) memakai return value method; dua titik (..) mengabaikannya dan meneruskan objek.

2. Cascade pada hasil yang ingin dipakai

dart
void main() {
  var list = <int>[]
    ..add(1)
    ..add(2);
  // var x = list..length; // x adalah list, BUKAN 3!
  var panjang = list.length; // BENAR: 2
  print(panjang);
}

Ingat: cascade selalu menghasilkan objeknya sendiri, bukan hasil operasi terakhir.

3. Cascade terlalu panjang

Rantai 15 operasi menjadi sulit dibaca dan di-debug (error di tengah rantai sulit dilacak barisnya). Batas wajar: 4-6 operasi. Lebih dari itu, pecah jadi beberapa statement.

Kesimpulan

.. merangkai operasi pada objek yang sama, ?.. versi aman-null. Ideal untuk konfigurasi builder dan perakitan bertahap. Ingat bedanya dengan . biasa.

Catatan teknis: Cascade juga bisa dipakai untuk assignment: obj..x = 1..y = 2. Dan di Flutter, cascade sering dipakai untuk mengkonfigurasi controller: TextEditingController()..text = 'isi'.

Tantangan

Rakit query URL

Pakai StringBuffer + cascade untuk membangun query URL dari map {'q': 'dart', 'page': '2', 'sort': 'asc'} menjadi 'q=dart&page=2&sort=asc'. Tanpa cascade dilarang!

text
void main() {
  var params = {'q': 'dart', 'page': '2', 'sort': 'asc'};
  var sb = StringBuffer();
  // TODO: cascade write '&' di antara pasangan, tanpa '&' di akhir
  // Petunjuk: pakai entries.toList() + index
  print(sb.toString());
}