Arrays
Ordered lists of values — how to create them, walk them, change them, and the methods you will use every day.
A scalar value (a single number, string, or boolean) is rarely enough. Most real-world data is a collection — a list of users, a row of pixels, a stack of moves. JavaScript's most fundamental collection is the array.
Creating arrays
An array is written with square brackets and commas:
JavaScript arrays can hold anything: numbers, strings, booleans, other arrays, objects, even functions. They are dynamically sized — you don't declare a length up front.
Length
Every array has a .length property — the number of elements in
it.
Indexing: zero-based
Read or write an element by its index, starting at 0.
That last block is a classic JavaScript surprise: setting an index
beyond the current length silently grows the array, filling the
gap with "empty slots". Real code almost never does this on
purpose — use .push instead.
Adding and removing elements
| Method | Where | Returns |
|---|---|---|
arr.push(x) | end (add) | new length |
arr.pop() | end (remove) | the removed element |
arr.unshift(x) | start (add) | new length |
arr.shift() | start (remove) | the removed element |
These four methods (push, pop, shift, unshift) mutate
the array — they change it in place. That is important to keep in
mind, especially when an array is shared across functions.
Iterating
We met loops in the control-flow chapter. Recall:
Slicing and copying
Two methods that look similar but are completely different:
slice(start, end)returns a new array with a portion of the original. The original is not modified.splice(start, deleteCount, ...newItems)mutates the array in place. Powerful but sharp.
When in doubt, prefer non-destructive operations. The
"functional" methods we will see in the next chapter (map,
filter, reduce) are all non-destructive, which makes them much
easier to reason about.
Useful array methods
A starter set, with the most common patterns:
The string-sort-by-default trap is famous. If you call .sort()
on an array of numbers expecting [2,4,10,33] and you get
[10,2,33,4], this is why. Always pass a comparator for numbers.
Spread and destructuring
Two pieces of modern syntax that come up everywhere with arrays.
Spread: unpack an array
Destructuring: pull elements out by position
Destructuring is a huge readability win. Once you internalise
it, you stop writing xs[0], xs[1], xs[2] and start writing
const [first, second, third] = xs.
Arrays are objects (and references)
A subtle but important point: arrays in JavaScript are a kind of object. That means they are passed by reference — when you assign an array to another variable or pass it to a function, you are sharing the same underlying array.
This is the same point we noted about objects in the variables
chapter: const protects the binding, not the contents.
const a = [1,2,3]; a.push(4) is perfectly legal — you cannot
reassign a, but you can modify what it points to.
Quick visual: an array in memory
Two variables, one array. Changing the array through either variable affects what both see.
A multi-file array example
A small two-file program demonstrates the typical shape: a module that owns the array operations, and a driver that uses them.
Challenge
Write a function rotate(xs, k) that returns a new array equal to xs rotated to the right by k positions. The original xs must not be modified.
Examples:
rotate([1, 2, 3, 4, 5], 1)→[5, 1, 2, 3, 4]rotate([1, 2, 3, 4, 5], 2)→[4, 5, 1, 2, 3]rotate([1, 2, 3, 4, 5], 5)→[1, 2, 3, 4, 5](full rotation)rotate([1, 2, 3, 4, 5], 7)→[4, 5, 1, 2, 3](k larger than length wraps)rotate([], 3)→[]
Hint: use the modulo operator (%) to handle k larger than the array length, then combine slice with the spread operator.
Two variables point to the same array: const a = [1, 2, 3]; const b = a;. You then call b.push(99). What is a?
[1, 2, 3] — a is independent of b
[1, 2, 3, 99] — a and b reference the same array, so changes through one are visible through the other
undefined — pushing through b clears a
A TypeError is thrown