CodeBlanks Logo Icon CodeBlanks

Discriminated union nedir?

Etiketli union'ları öğrenirsin.

Discriminated union nedir?

Discriminated union, her üyenin ortak bir özelliğe (discriminant) sahip olduğu ve bu özelliğin her üyede farklı bir literal değer aldığı union türüdür. Ortak alan sayesinde TypeScript, bir koşulla union'ı tek bir üyeye daraltabilir. Bu, karmaşık veri modellerini güvenli şekilde işlemeyi sağlar.

type Shape =
  | { kind: "circle"; radius: number }
  | { kind: "square"; size: number };

function area(s: Shape): number {
  if (s.kind === "circle") {
    return Math.PI * s.radius ** 2;  // circle
  }
  return s.size ** 2;  // square
}

Discriminant alanı

Discriminant alanı genellikle kind, type veya tag olarak adlandırılır. Her üye bu alana kendi benzersiz literal değerini verir; örneğin "circle", "square". Koşul bu literal değeri kontrol ettiğinde TypeScript union'ı o üyeye daraltır.

type Action =
  | { type: "add"; item: string }
  | { type: "remove"; id: number };

function run(a: Action) {
  if (a.type === "add") {
    a.item;  // string
  } else {
    a.id;    // number
  }
}

Uygulama Discriminated union ile şekil alanı

Shape discriminated union türünü tanımla: "circle" (radius: number) ve "square" (size: number) üyeleri, kind discriminant alanıyla. area(s: Shape): number fonksiyonunu yaz. Eğer s.kind === "circle" ise Math.PI * s.radius ** 2 döndür; değilse s.size ** 2 döndür. console.log(area({ kind: "circle", radius: 2 })) ve console.log(area({ kind: "square", size: 3 })) ile sonuçları yazdır.

Başlangıç kodu

index.ts
// Shape discriminated union türünü tanımla (kind discriminant, circle ve square üyeleri)

// area(s: Shape): number fonksiyonunu kind kontrolüyle yaz

// circle ve square şekillerinin alan sonuçlarını yazdır

Örnek çözüm

index.ts
type Shape =
  | { kind: "circle"; radius: number }
  | { kind: "square"; size: number };

function area(s: Shape): number {
  if (s.kind === "circle") {
    return Math.PI * s.radius ** 2;
  }
  return s.size ** 2;
}

console.log(area({ kind: "circle", radius: 2 }));
console.log(area({ kind: "square", size: 3 }));

Beklenen çıktı

12.566370614359172
9

Soru ve cevaplar

Dersin sorularını cevaplarıyla birlikte inceleyebilirsin. Kendini denemek istersen dersi interaktif olarak çöz.

1 Bir union'ın discriminated sayılması için ne gerekir?

  • Tüm üyelerin aynı yapıda olması
  • En az bir özelliğin opsiyonel olması
  • Her üyenin bir sınıf olması
  • Ortak bir özelliğin her üyede farklı literal değer alması Doğru cevap

Açıklama: Discriminated union için ortak bir discriminant alanı gerekir ve bu alan her üyede farklı bir literal değer alır; böylece TypeScript koşulla union'ı tek üyeye daraltabilir.

2 Discriminant alanı

Soru
type Shape =
  | { kind: "circle"; radius: number }
  | { kind: ____; size: number };

function area(s: Shape) {
  if (s.kind === "square") return s.size ** 2;
  return Math.PI * s.radius ** 2;
}
Cevap
type Shape =
  | { kind: "circle"; radius: number }
  | { kind: "square"; size: number };

function area(s: Shape) {
  if (s.kind === "square") return s.size ** 2;
  return Math.PI * s.radius ** 2;
}

Açıklama: Her üyenin discriminant alanı farklı bir literal değer almalıdır; "square" üyesi "circle"dan farklı değer kullanır.

3 Discriminated union parçaları

Kavram Anlamı
Discriminant alanı her üyede farklı literal değer
Ortak özellik tüm üyelerde bulunur
Narrowing discriminant kontrolüyle yapılır
Union üye türlerin birleşimi

İleri seviye bölümündeki tüm dersler