Skip to content
Educora
Beginner15 min2 / 8

Basic types and inference

Meet `string`, `number`, `boolean`, arrays and tuples, see how TypeScript works out types by itself, and learn the difference between `any` and `unknown` and what literal types are.

Check yourself
In this lesson you will learn
  • Annotate variables with the basic types and know when to rely on inference
  • Describe array and tuple types
  • Explain the difference between any and unknown
  • Restrict values with literal types

In JavaScript a variable can hold a number today, a string tomorrow and an object the day after — nobody complains. In a small script that is convenient, but in a big program it causes confusion: to know what is inside score, you have to trace the whole code. In TypeScript every variable has a type, and it stays the same for the variable's whole life. The best part: most of the time you don't even have to write the types yourself.

Primitive types

Each of the primitive values you know from the JavaScript course has its own type in TypeScript. The three you will use most are string for text, number for any number — whole or fractional — and boolean for true/false. Type names are written in lowercase.

TypeScript
let city: string = 'Baku';
let temperature: number = 23.5;
let isSunny: boolean = true;

temperature = 25;
console.log(`${city}: ${temperature}°C, sunny: ${isSunny}`);
Expected output
Baku: 25°C, sunny: true

Type inference

Definition
Type inference

TypeScript working out a variable's type by itself from the first value it is given. When you write let score = 10 there is no annotation, yet score already has the type number.

TypeScript
let score = 10;
score = score + 5;
score = 'fifteen';
Text
score.ts:3:1 - error TS2322: Type 'string' is not assignable to type 'number'.

3 score = 'fifteen';
  ~~~~~
We never wrote a type, but TypeScript remembers that score is a number.

If you hover over a variable in your editor, you will see the type TypeScript inferred: let score: number. The rule is simple: if you give a variable a value right away, don't write the type — inference is enough. Write types for variables declared without a value and for function parameters, which we will cover in the next lesson.

Arrays and tuples

An array type is written as the element type followed by square brackets: number[] is an array of numbers. You can also write the same thing as Array<number>. A tuple is an array whose length and the type of each position are known in advance: [string, number] means a string, then a number, and exactly two elements.

TypeScript
const scores: number[] = [90, 75, 88];
const names: Array<string> = ['Aysel', 'Murad'];
scores.push(100);

const entry: [string, number] = ['Leyla', 17];
const [name, age] = entry;

console.log(scores.length, names[1]);
console.log(`${name} is ${age}`);
Expected output
4 Murad
Leyla is 17
Destructuring the tuple: name automatically becomes a string and age a number.
TypeScript
const scores: number[] = [90, 75, 88];
scores.push('ninety');

const point: [number, number] = [40.4, 49.9, 0];
Text
lists.ts:2:13 - error TS2345: Argument of type 'string' is not assignable to parameter of type 'number'.

2 scores.push('ninety');
              ~~~~~~~~

lists.ts:4:7 - error TS2322: Type '[number, number, number]' is not assignable to type '[number, number]'.
  Source has 3 element(s) but target allows only 2.

4 const point: [number, number] = [40.4, 49.9, 0];
        ~~~~~
You can't add a string to an array of numbers, and you can't put three elements into a two-element tuple.

any and unknown

Sometimes a value's type is not known in advance — for example, it comes from a server or from JSON.parse. There are two special types for this. any switches checking off completely: you can write any operation with such a value, and the mistakes show up at runtime again. unknown means “I don't know yet”: any value can be stored in it, but you must check its type before you use it.

TypeScript
let risky: any = 'hello';
let fromServer: unknown = 'hello';

risky.toFixed(2);
fromServer.toUpperCase();
Text
data.ts:5:1 - error TS18046: 'fromServer' is of type 'unknown'.

5 fromServer.toUpperCase();
  ~~~~~~~~~~
Line 4 compiles without an error but will crash when it runs — a string has no toFixed method. unknown points out the problem right away.

This is how you work with unknown correctly: first you check with typeof, and inside the if block TypeScript knows the value's exact type.

TypeScript
function describe(value: unknown): string {
  if (typeof value === 'string') {
    return `a string of length ${value.length}`;
  }
  if (typeof value === 'number') {
    return `the number ${value.toFixed(1)}`;
  }
  return 'something else';
}

console.log(describe('Baku'));
console.log(describe(3.14159));
console.log(describe(true));
Expected output
a string of length 4
the number 3.1
something else

Literal types

A type can also be one exact value. The type 'left' | 'right' accepts only one of these two strings; the | sign means “or”. Such literal types protect you from typos, and the editor suggests the possible values by itself. Interestingly, when you write const planet = 'Earth', the type of planet is not string but exactly 'Earth' — after all, a constant will never change. With let the type would be string.

TypeScript
let direction: 'left' | 'right' = 'left';
direction = 'right';
direction = 'up';
Text
direction.ts:3:1 - error TS2322: Type '"up"' is not assignable to type '"left" | "right"'.

3 direction = 'up';
  ~~~~~~~~~
In error messages, literal types are shown in double quotes: "up".
1 / 6

Key points

  • The main primitive types are string, number and boolean — always lowercase.
  • If a variable gets a value right away, TypeScript infers the type itself; the type can't change later.
  • number[] is an array, while [string, number] is a tuple with a fixed length and fixed position types.
  • any turns checking off; unknown is safe because it demands a check before use.
  • Literal types ('left' | 'right') limit a value to a few exact options.

Check yourself

10 questions. Every correct answer earns XP.

1 / 10
Which type does TypeScript infer for count in let count = 5;?