// Primitive types
let name: string = 'Alice';
let age: number = 30;
let isActive: boolean = true;
let nothing: null = null;
let notDefined: undefined = undefined;
// Arrays
let numbers: number[] = [1, 2, 3];
let names: Array<string> = ['Alice', 'Bob'];
// Tuple - fixed length array with specific types
let tuple: [string, number] = ['Alice', 30];
// Any and Unknown
let flexible: any = 'anything'; // Avoid when possible
let safe: unknown = 'must check'; // Safer than any
// Void and Never
function log(msg: string): void { console.log(msg); }
function error(msg: string): never { throw new Error(msg); }
// TypeScript infers types automatically
let message = 'Hello'; // inferred as string
let count = 42; // inferred as number
let items = [1, 2, 3]; // inferred as number[]
// Contextual typing
const names = ['Alice', 'Bob'];
names.forEach(name => { // name is inferred as string
console.log(name.toUpperCase());
});
// Define object shape
interface User {
id: number;
name: string;
email?: string; // Optional property
readonly createdAt: Date; // Cannot be modified
}
// Extend interfaces
interface Admin extends User {
role: 'admin';
permissions: string[];
}
// Function interface
interface SearchFunc {
(query: string, limit?: number): Promise<User[]>;
}
// Index signatures
interface Dictionary {
[key: string]: string;
}
// Type alias for primitives and unions
type ID = string | number;
type Status = 'pending' | 'active' | 'inactive';
// Type alias for objects
type Point = {
x: number;
y: number;
};
// Intersection types
type Employee = User & {
department: string;
salary: number;
};
// Template literal types
type EventName = `on${Capitalize<string>}`;
// Union types - one of several types
type Result = string | number | boolean;
type Status = 'success' | 'error' | 'loading';
function printId(id: string | number) {
if (typeof id === 'string') {
console.log(id.toUpperCase());
} else {
console.log(id);
}
}
// Intersection types - combine multiple types
type Name = { firstName: string; lastName: string };
type Age = { age: number };
type Person = Name & Age;
// Generic function
function identity<T>(arg: T): T {
return arg;
}
const result = identity<string>('hello');
// Generic interface
interface Container<T> {
value: T;
getValue(): T;
}
// Generic constraints
function getLength<T extends { length: number }>(item: T): number {
return item.length;
}
// Multiple type parameters
function pair<K, V>(key: K, value: V): [K, V] {
return [key, value];
}
// Generic defaults
interface Response<T = any> {
data: T;
status: number;
}
interface User {
id: number;
name: string;
email: string;
age: number;
}
// Partial - all properties optional
type PartialUser = Partial<User>;
// Required - all properties required
type RequiredUser = Required<User>;
// Readonly - all properties readonly
type ReadonlyUser = Readonly<User>;
// Pick - select specific properties
type UserPreview = Pick<User, 'id' | 'name'>;
// Omit - exclude specific properties
type UserWithoutEmail = Omit<User, 'email'>;
// Record - construct object type
type UserRoles = Record<string, 'admin' | 'user' | 'guest'>;
// Extract and Exclude
type T1 = Extract<'a' | 'b' | 'c', 'a' | 'f'>; // 'a'
type T2 = Exclude<'a' | 'b' | 'c', 'a'>; // 'b' | 'c'
// ReturnType and Parameters
type Fn = (a: string, b: number) => boolean;
type FnReturn = ReturnType<Fn>; // boolean
type FnParams = Parameters<Fn>; // [string, number]
class Person {
// Properties with access modifiers
public name: string;
private age: number;
protected id: number;
readonly createdAt: Date;
// Parameter properties shorthand
constructor(
public firstName: string,
private lastName: string
) {
this.createdAt = new Date();
}
// Method
greet(): string {
return `Hello, ${this.firstName}`;
}
// Getter and Setter
get fullName(): string {
return `${this.firstName} ${this.lastName}`;
}
set fullName(value: string) {
[this.firstName, this.lastName] = value.split(' ');
}
// Static members
static species = 'Homo sapiens';
static create(name: string): Person {
return new Person(name, '');
}
}
// Abstract class
abstract class Animal {
abstract makeSound(): void;
move(): void {
console.log('Moving...');
}
}
// typeof guard
function process(value: string | number) {
if (typeof value === 'string') {
return value.toUpperCase();
}
return value * 2;
}
// instanceof guard
class Dog { bark() {} }
class Cat { meow() {} }
function speak(animal: Dog | Cat) {
if (animal instanceof Dog) {
animal.bark();
} else {
animal.meow();
}
}
// in operator guard
interface Fish { swim(): void }
interface Bird { fly(): void }
function move(animal: Fish | Bird) {
if ('swim' in animal) {
animal.swim();
} else {
animal.fly();
}
}
// Custom type guard
function isString(value: unknown): value is string {
return typeof value === 'string';
}
// as syntax (preferred)
const input = document.getElementById('input') as HTMLInputElement;
// Angle bracket syntax
const input2 = <HTMLInputElement>document.getElementById('input');
// Non-null assertion
function getValue(map: Map<string, string>, key: string) {
return map.get(key)!; // Assert value is not undefined
}
// const assertion
const config = {
endpoint: '/api',
timeout: 3000
} as const; // Makes all properties readonly and literal types
// Numeric enum
enum Direction {
Up, // 0
Down, // 1
Left, // 2
Right // 3
}
// String enum
enum Status {
Pending = 'PENDING',
Active = 'ACTIVE',
Inactive = 'INACTIVE'
}
// Const enum (inlined at compile time)
const enum Color {
Red = '#ff0000',
Green = '#00ff00',
Blue = '#0000ff'
}
// Usage
let dir: Direction = Direction.Up;
let status: Status = Status.Active;
// Create new type by transforming properties
type Readonly<T> = {
readonly [P in keyof T]: T[P];
};
type Optional<T> = {
[P in keyof T]?: T[P];
};
type Nullable<T> = {
[P in keyof T]: T[P] | null;
};
// Conditional types
type NonNullable<T> = T extends null | undefined ? never : T;
type Flatten<T> = T extends Array<infer U> ? U : T;
// Key remapping
type Getters<T> = {
[K in keyof T as `get${Capitalize<string & K>}`]: () => T[K];
};
// Type-only imports
import type { User } from './types';
import { type User, createUser } from './user';
// Declare module augmentation
declare module 'express' {
interface Request {
user?: User;
}
}
// Ambient declarations for JS libraries
declare const $: (selector: string) => any;
// Declaration files (.d.ts)
declare module '*.css' {
const styles: { [className: string]: string };
export default styles;
}
// Discriminated unions
type Result<T> =
| { success: true; data: T }
| { success: false; error: string };
function handleResult<T>(result: Result<T>) {
if (result.success) {
console.log(result.data);
} else {
console.error(result.error);
}
}
// Builder pattern with method chaining
class QueryBuilder {
select(fields: string[]): this { return this; }
where(condition: string): this { return this; }
orderBy(field: string): this { return this; }
}
// Exhaustive checking
type Shape = 'circle' | 'square' | 'triangle';
function getArea(shape: Shape): number {
switch (shape) {
case 'circle': return Math.PI;
case 'square': return 1;
case 'triangle': return 0.5;
default:
const _exhaustive: never = shape;
return _exhaustive;
}
}