Data types and typeof

Learn the seven primitive types and objects, the difference between null and undefined, and how to check a value's type.

  • Beginner
  • 7 min read
  • Updated 17 Oct 2026

What you will learn

  • Name the primitive types
  • Check a value's type
  • Explain the difference between null and undefined
  • Explain why primitives are immutable

Every value in JavaScript has a type: a number, some text, true or false, and so on. The type decides what you can do with a value and how operators treat it. This lesson introduces every type in the language and shows how to check which one you have.

Types belong to values, not variables

JavaScript is dynamically typed. You never say what type a variable holds; the value carries its own type. The same let can hold a number and later a string:

JavaScript
let answer = 42;
answer = "forty-two";

This is legal, but changing a variable's type part-way through usually makes code harder to follow. Keep each variable to one type.

The primitive types

JavaScript has seven primitive types. A primitive is a simple value that is not an object.

TypeExample valuesUsed for
string"hello", 'Ada', template literalsText
number42, 3.14, -7, NaN, InfinityNumbers of all kinds
booleantrue, falseYes or no
undefinedundefinedA value that has not been set
nullnullA deliberately empty value
bigint9007199254740993nWhole numbers too large for number
symbolSymbol("id")Unique identifiers

string

Strings hold text. You can use double quotes, single quotes or backticks. Lesson 6 covers strings in detail.

JavaScript
const city = "Bristol";
const greeting = 'Hello';
const message = `Welcome to ${city}`;

number

JavaScript has a single number type for whole numbers and decimals alike:

JavaScript
const age = 34;
const price = 19.99;
const temperature = -4;

It also includes three special values: Infinity, -Infinity and NaN, which stands for "not a number" and is the result of maths that makes no sense:

JavaScript
console.log(10 / 0);
// Infinity
console.log(Number("hello"));
// NaN

Lesson 7 covers numbers and their surprises.

boolean

A boolean is either true or false. Comparisons produce booleans:

JavaScript
const isMember = true;
const isAdult = 34 >= 18;
console.log(isAdult);
// true

undefined and null

Both mean "no value", but they are used differently:

  • undefined means a value has not been set. JavaScript produces it on its own: a let with no value, a missing function argument, an object property that does not exist.
  • null means "intentionally empty". JavaScript itself rarely produces it; you, or an API, choose to use it. For example, document.querySelector returns null when no element matches.
JavaScript
let selectedCourse;
console.log(selectedCourse);
// undefined

const middleName = null; // We know there is no middle name

A useful rule: let JavaScript produce undefined, and use null yourself when you want to say "empty on purpose".

bigint and symbol

You will rarely need these as a beginner. A bigint holds whole numbers of any size, written with an n on the end. A symbol is a guaranteed-unique value, mostly used as a special kind of object key. Lesson 52 covers symbols.

Objects

Everything that is not a primitive is an object. Objects group values together and can be changed after they are created:

JavaScript
const user = { name: "Ada", role: "admin" };
const scores = [10, 20, 30];
function greet() {
  return "Hello";
}

The plain object, the array and the function are all objects. So are dates, regular expressions, maps and the DOM elements on a page. Lessons 12 and 13 introduce arrays and objects properly.

Primitives are immutable

You cannot change a primitive value itself, only replace it with a new one. String methods, for example, always return a new string and leave the original unchanged:

JavaScript
const word = "hello";
const shout = word.toUpperCase();

console.log(word);
// hello
console.log(shout);
// HELLO

Objects are different: you can change their contents in place. This difference, and what it means for copying, comes up again in lesson 40.

Checking a type with typeof

The typeof operator returns a string naming a value's type:

JavaScript
console.log(typeof "hello");
// string
console.log(typeof 42);
// number
console.log(typeof true);
// boolean
console.log(typeof undefined);
// undefined
console.log(typeof 10n);
// bigint
console.log(typeof Symbol("id"));
// symbol
console.log(typeof { name: "Ada" });
// object
console.log(typeof function () {});
// function

Functions get their own answer, "function", even though they are objects. That is convenient for checking whether something can be called.

typeof is also safe to use on a name that was never declared. It returns "undefined" rather than throwing an error, which is why older code uses it to check whether a feature exists.

Two typeof surprises

typeof null is "object".

JavaScript
console.log(typeof null);
// object

This is a bug from the first version of JavaScript. Fixing it would break existing websites, so it stays. To check for null, compare directly:

JavaScript
const value = null;
console.log(value === null);
// true

Arrays are "object" too.

JavaScript
console.log(typeof [1, 2, 3]);
// object
console.log(Array.isArray([1, 2, 3]));
// true

Use Array.isArray() to check for an array.

NaN is a number

JavaScript
console.log(typeof NaN);
// number

NaN is a special number value that means a calculation failed. Check for it with Number.isNaN():

JavaScript
console.log(Number.isNaN(Number("abc")));
// true

A quick type-checking guide

To check forUse
string, number, boolean, bigint, symbol, functiontypeof value === "string" and so on
undefinedvalue === undefined
nullvalue === null
arrayArray.isArray(value)
NaNNumber.isNaN(value)
plain objecttypeof value === "object" && value !== null && !Array.isArray(value)

You do not need to check types everywhere. Check at the edges of your program, where data arrives from a form, a file or a network request. Inside your own code, you usually know what you have.

Types and conversion

Because types belong to values, JavaScript sometimes converts a value from one type to another to make an operation work. This is called type coercion:

JavaScript
console.log("5" + 1);
// 51
console.log("5" * 2);
// 10

The + operator joins strings, so the number becomes text. The * operator only works on numbers, so the string becomes a number. These rules are a common source of bugs, and lesson 5 explains them and how to avoid them.

Summary

  • Types belong to values. A variable can hold any type, but keep each variable to one.
  • The seven primitive types are string, number, boolean, undefined, null, bigint and symbol.
  • Everything else, including arrays and functions, is an object.
  • undefined means "not set"; null means "empty on purpose".
  • Primitives are immutable; objects can be changed in place.
  • typeof names a value's type, but returns "object" for null and arrays. Use === null and Array.isArray() instead.

Further reading