← Back to libraryQuestion 226 of 468
🔷TypeScriptAdvanced

Structural Typing (Duck Typing)

📌 Definition:

TypeScript uses STRUCTURAL typing: compatibility is based on a type's SHAPE (its members), not its name or declared inheritance. If it has the required members, it fits — 'if it walks like a duck'.

📖 Detailed Explanation:

Two independently declared types with the same structure are interchangeable, and a value with EXTRA properties still satisfies a type needing a subset (with a special exception for object literals, which get excess-property checks). This differs from nominal typing (Java/C#) where names/inheritance decide compatibility. Structural typing makes TypeScript flexible — a function needing { id: number } accepts anything with a numeric id — but can surprise people expecting nominal behavior. To force distinctness (a 'branded' type), you add a private/unique marker. Understanding this explains why unrelated objects are assignable when shapes match.

🔑 Key Points:
  • Compatibility by SHAPE (members), not name/inheritance
  • A value with the required members fits (extra props OK, except object literals)
  • Differs from nominal typing (Java/C#)
  • Use branded types to force nominal-like distinctness
🌍 Real-World Example:

A logging helper typed to accept { message: string } will accept an Error, an API response, or any object that has a message field — no shared base class required, thanks to structural typing.

🎯 Scenario-Based Interview Question:

In Java, two classes with identical fields are NOT interchangeable. Why ARE they in TypeScript, and when can that bite you?