W3docs

JavaScript Data Types

Learn the eight JavaScript data types — number, string, boolean, null, undefined, bigint, symbol, and object — with typeof operator and coercion rules.

Introduction to JavaScript Data Types

JavaScript is a dynamically typed language: you never declare the type of a variable, and a variable can hold a value of any type — even a different type later on. Because the engine, not you, tracks types at runtime, knowing exactly how each type behaves is what separates predictable code from baffling bugs.

let x = 42;        // x is now a number
x = "forty-two";   // the same variable now holds a string — perfectly legal

The language defines eight data types: seven primitives and one non-primitive (object). The page below covers each one, how to check it with typeof, and the coercion rules that trip up most beginners.

Primitive Data Types

A primitive is a value that is not an object and has no methods of its own. Primitives are immutable — you can never change a primitive value, only replace the variable that holds it.

  • Number: Integer or floating-point values, plus the special values Infinity, -Infinity, and NaN (Not a Number). See Numbers.
  • String: Textual data, enclosed in double quotes, single quotes, or backticks. See Strings.
  • Boolean: One of two logical values, true or false.
  • Undefined: A variable that has been declared but not assigned a value.
  • Null: The intentional absence of any object value.
  • BigInt: Integers beyond the Number type's safe limit. See BigInt.
  • Symbol: A guaranteed-unique identifier, mostly used as object keys. See Symbol type.

Non-Primitive Data Type

  • Object: A collection of key/value properties used to model complex data. Arrays, functions, dates, and most built-ins are all objects under the hood. See Objects.

Checking a Type with typeof

To find out what type a value is, JavaScript provides the typeof operator. It returns a string such as "number", "string", or "boolean".

javascript— editable

Two results surprise newcomers:

  • typeof null returns "object". This is a bug from the very first version of JavaScript that can never be fixed without breaking the web — just memorize it.
  • typeof a function returns "function". Functions are really objects, but typeof treats them specially so you can detect callables.

Working with Primitive Data Types

Below, each primitive is shown with a minimal example you can run.

Number: The Backbone of Mathematical Operations

let age = 25;       // Integer
let price = 99.99;  // Floating-point
console.log(typeof age);   // "number"
console.log(0.1 + 0.2);    // 0.30000000000000004  (floating-point rounding)

A single number type covers both integers and decimals. Because numbers use 64-bit floating point, fractional math is not always exact — 0.1 + 0.2 is the classic example. Numbers also include Infinity and NaN; NaN is famously not equal to itself, so use Number.isNaN(x) to test for it.

String: More Than Just Text

let greeting = "Hello, world!";
let name = 'Ada';
let response = `Hi, ${name}!`; // template literal with interpolation
console.log(typeof greeting); // "string"
console.log(response);        // "Hi, Ada!"

Strings are immutable: methods like toUpperCase() return a new string instead of changing the original. Backtick strings (template literals) let you embed ${expressions} and span multiple lines. Explore the full toolkit in Strings.

Boolean: The Binary Decision Maker

let isAvailable = true;
let age = 25;
let isAdult = age >= 18; // comparisons produce booleans
console.log(typeof isAvailable); // "boolean"
console.log(isAdult);            // true

Booleans drive every conditional and loop. Any value can also be coerced to a boolean — see the truthy/falsy table below.

Undefined and Null: The Absence of Value

let notAssigned;          // declared but never given a value
let emptyOnPurpose = null; // deliberately "nothing"
console.log(typeof notAssigned);  // "undefined"
console.log(typeof emptyOnPurpose); // "object" (the typeof null quirk)
console.log(null == undefined);   // true  (loose equality)
console.log(null === undefined);  // false (strict equality — different types)

Use undefined for "no value yet" (it's what JavaScript assigns automatically), and null for "intentionally empty." They are loosely equal (==) but not strictly equal (===).

BigInt: Handling Large Numbers

const big = 9007199254740991n; // note the trailing n
console.log(typeof big);     // "bigint"
console.log(big + 1n);       // 9007199254740992n

Number can only safely represent integers up to Number.MAX_SAFE_INTEGER (about 9 quadrillion). For anything larger — cryptography, high-precision IDs — use BigInt, written with a trailing n. You cannot mix BigInt and Number in the same arithmetic without explicit conversion. More in BigInt.

Symbol: Ensuring Uniqueness

javascript— editable

Each Symbol() call returns a brand-new, unique value even if the description text matches. Symbols are used as collision-proof object keys, for example to attach metadata without clashing with normal string keys. See Symbol type.

Objects: The Building Blocks of Complex Structures

In JavaScript, objects store collections of related data as key/value pairs and are the foundation for arrays, functions, and most built-ins.

let person = {
  name: "John",
  age: 30,
  isStudent: false
};
console.log(typeof person);     // "object"
console.log(typeof [1, 2, 3]);  // "object"  (arrays are objects)
console.log(Array.isArray([1])); // true — the reliable way to detect arrays

Objects are mutable — unlike primitives, you can add, change, and delete their properties. They are also compared by reference, not by value: two objects with identical contents are not === equal.

Type Coercion and Conversion

Because JavaScript is dynamically typed, it often coerces a value from one type to another during an operation. This is convenient but a common source of surprises.

javascript— editable

When in doubt, convert explicitly with Number(), String(), or Boolean() instead of relying on automatic coercion.

Truthy and Falsy Values

When a value is used where a boolean is expected (an if, &&, ||), it is coerced. Exactly six values are falsy; everything else is truthy:

// falsy: false, 0, "", null, undefined, NaN
if ("") console.log("won't run");      // "" is falsy
if ("0") console.log("this runs");     // non-empty string is truthy
if ([]) console.log("this runs too");  // empty array is truthy!

A frequent gotcha: an empty array [] and empty object {} are truthy, even though "" and 0 are falsy.

Summary

JavaScript has eight data types — seven primitives (number, string, boolean, undefined, null, bigint, symbol) and the object. typeof reports the type, with the well-known quirks that typeof null is "object" and functions report "function". Primitives are immutable and compared by value; objects are mutable and compared by reference. Master coercion and the truthy/falsy rules and most "weird JavaScript" disappears. Next, see how values are stored in Variables.

Practice

Practice
Which of the following are valid JavaScript data types?
Which of the following are valid JavaScript data types?
Practice
What does typeof null return in JavaScript?
What does typeof null return in JavaScript?
Was this page helpful?