TypeScript discriminated unions, also known as tagged unions, are a powerful feature enabling developers to model complex data structures with clarity and type safety. These unions involve creating a common property, known as a discriminator, which serves to distinguish between different shapes or types within the union.
By relying on discriminators, TypeScript enables precise type inference and facilitates exhaustive checks, reducing the risk of runtime errors. Discriminated unions are widely used to express various scenarios, such as handling different shapes of objects or representing a set of string literals, enhancing code readability and robustness.
interface Car {
type: "car";
brand: string;
}
interface Bicycle {
type: "bicycle";
color: string;
}
type Vehicle = Car Bicycle;
function displayVehicleInfo(vehicle: Vehicle): void {
switch (vehicle.type) {
case "car":
console.log(`Car - Brand: ${vehicle.brand}`);
break;
case "bicycle":
console.log(`Bicycle - Color: ${vehicle.color}`);
break;
}
}
const myCar: Vehicle = { type: "car", brand: "Toyota" };
const myBicycle: Vehicle = { type: "bicycle", color: "Blue" };
displayVehicleInfo(myCar); // Output: Car - Brand: Toyota
displayVehicleInfo(myBicycle); // Output: Bicycle - Color: Blue
Running the TypeScript compiler (tsc) will generate the following JavaScript code:
function displayVehicleInfo(vehicle) {
switch (vehicle.type) {
case "car":
console.log(`Car - Brand: ${vehicle.brand}`);
break;
case "bicycle":
console.log(`Bicycle - Color: ${vehicle.color}`);
break;
}
}
const myCar = { type: "car", brand: "Toyota" };
const myBicycle = { type: "bicycle", color: "Blue" };
displayVehicleInfo(myCar); // Output: Car - Brand: Toyota
displayVehicleInfo(myBicycle); // Output: Bicycle - Color: Blue
Conclusion
Discriminated unions provide a way to model complex data scenarios in a type-safe manner, ensuring that the TypeScript compiler can accurately infer and narrow down types based on discriminant properties. This results in code that is both expressive and resilient, as it facilitates pattern matching and exhaustive checks, reducing the likelihood of runtime errors.