Primitive Types
TypeScript includes all JavaScript primitives plus additional type annotations.
// String
let firstName: string = "Alice";
let greeting: string = `Hello, ${firstName}`;
// Number (integers and floats)
let age: number = 30;
let price: number = 19.99;
let hex: number = 0xff;
let binary: number = 0b1010;
// Boolean
let isActive: boolean = true;
let hasPermission: boolean = false;
// Null and Undefined
let nothing: null = null;
let notDefined: undefined = undefined;
// BigInt (ES2020+)
let bigNumber: bigint = 9007199254740991n;
// Symbol
let uniqueKey: symbol = Symbol("key");
Arrays
// Two ways to declare arrays
let numbers: number[] = [1, 2, 3, 4, 5];
let strings: Array<string> = ["a", "b", "c"];
// Mixed arrays (avoid when possible)
let mixed: (string | number)[] = [1, "two", 3];
// Readonly arrays
let readonlyNumbers: readonly number[] = [1, 2, 3];
// readonlyNumbers.push(4); // Error: Property 'push' does not exist
// Array methods are type-aware
const doubled = numbers.map(n => n * 2); // number[]
const filtered = strings.filter(s => s.length > 1); // string[]
Tuples
Fixed-length arrays with specific types at each position:
// Tuple: [string, number]
let person: [string, number] = ["Alice", 30];
// Accessing tuple elements
const name = person[0]; // string
const age = person[1]; // number
// Tuple with optional element
let optionalTuple: [string, number?] = ["Bob"];
// Tuple with rest elements
let flexibleTuple: [string, ...number[]] = ["scores", 90, 85, 92];
// Named tuples (TypeScript 4.0+)
type Point = [x: number, y: number];
let coordinates: Point = [10, 20];
// Readonly tuple
const readonlyTuple: readonly [string, number] = ["Alice", 30];
// readonlyTuple[0] = "Bob"; // Error!
Enums
// Numeric enum (default)
enum Direction {
Up, // 0
Down, // 1
Left, // 2
Right // 3
}
let move: Direction = Direction.Up;
console.log(Direction.Up); // 0
console.log(Direction[0]); // "Up"
// String enum
enum Status {
Pending = "PENDING",
Active = "ACTIVE",
Completed = "COMPLETED",
Cancelled = "CANCELLED"
}
let orderStatus: Status = Status.Active;
// Const enum (inlined at compile time)
const enum HttpStatus {
OK = 200,
NotFound = 404,
ServerError = 500
}
// Heterogeneous enum (avoid)
enum Mixed {
No = 0,
Yes = "YES"
}
Any, Unknown, Never, Void
// any - disables type checking (avoid!)
let anything: any = 42;
anything = "string";
anything = true;
anything.nonExistentMethod(); // No error, but crashes at runtime
// unknown - type-safe any
let uncertain: unknown = 42;
uncertain = "string";
// uncertain.toUpperCase(); // Error! Must check type first
if (typeof uncertain === "string") {
console.log(uncertain.toUpperCase()); // OK
}
// void - function returns nothing
function logMessage(msg: string): void {
console.log(msg);
// no return statement
}
// never - function never returns
function throwError(message: string): never {
throw new Error(message);
}
function infiniteLoop(): never {
while (true) {}
}
Object Type
// Inline object type
let user: { name: string; age: number } = {
name: "Alice",
age: 30
};
// Optional properties
let config: { host: string; port?: number } = {
host: "localhost"
// port is optional
};
// Readonly properties
let point: { readonly x: number; readonly y: number } = {
x: 10,
y: 20
};
// point.x = 30; // Error!
// Index signatures
let dictionary: { [key: string]: number } = {
apple: 1,
banana: 2,
cherry: 3
};
dictionary["date"] = 4; // OK
Type Assertions
// Type assertion (you know more than TypeScript)
let someValue: unknown = "Hello, World!";
// Using 'as' syntax (preferred)
let strLength: number = (someValue as string).length;
// Using angle-bracket syntax (not in JSX)
let strLength2: number = (<string>someValue).length;
// DOM element assertion
const input = document.getElementById("myInput") as HTMLInputElement;
input.value = "Hello";
// Non-null assertion (use carefully!)
let maybeString: string | null = getValue();
let definitelyString: string = maybeString!; // Assert it's not null
Literal Types
// String literal types
let direction: "north" | "south" | "east" | "west";
direction = "north"; // OK
// direction = "up"; // Error!
// Numeric literal types
let diceRoll: 1 | 2 | 3 | 4 | 5 | 6;
diceRoll = 3; // OK
// diceRoll = 7; // Error!
// Boolean literal types
let trueOnly: true = true;
// Combining with other types
type HttpMethod = "GET" | "POST" | "PUT" | "DELETE";
function makeRequest(url: string, method: HttpMethod) {
// ...
}
makeRequest("/api/users", "GET"); // OK
// makeRequest("/api/users", "PATCH"); // Error!
Avoid 'any'
Using any defeats the purpose of TypeScript. Instead:
- • Use
unknownwhen you don't know the type - • Use generics for flexible but type-safe code
- • Use union types for multiple possibilities
Key Takeaways
- • Use primitive types: string, number, boolean
- • Arrays can be typed with
type[]orArray<type> - • Tuples are fixed-length typed arrays
- • Enums provide named constants
- • Prefer
unknownoverany - • Literal types restrict to specific values