JavaScript
3 min read
Updated 4 Aug 2026
Part 11 — Arrays
Method reference, reduce deeply, Creating & copying, Holes & sparse arrays ⚠️, Time complexity 🎯
Arrays are ordered, index-keyed objects with a magic length. They can be sparse (have holes).
Method reference#
| Method | Mutates? | Returns | Notes |
|---|---|---|---|
push/pop |
✅ | new length / removed | end operations, O(1) |
shift/unshift |
✅ | removed / new length | front ops, O(n) |
splice(i, del, ...add) |
✅ | removed items | insert/remove/replace |
sort(cmp) |
✅ | same array | default sorts as strings ⚠️ |
reverse |
✅ | same array | |
fill(v, s, e) |
✅ | same array | |
copyWithin |
✅ | same array | rarely used |
map(fn) |
❌ | new array | transform |
filter(fn) |
❌ | new array | keep truthy |
reduce(fn, init) |
❌ | any | fold; always pass init |
reduceRight |
❌ | any | right-to-left |
slice(s, e) |
❌ | new array | copy a range (also shallow-copies) |
concat(...) |
❌ | new array | merge |
flat(depth) |
❌ | new array | flatten nested |
flatMap(fn) |
❌ | new array | map then flat 1 |
find/findIndex |
❌ | item / index | first match |
findLast/findLastIndex 🟢 |
❌ | item / index | from the end |
some/every |
❌ | boolean | any / all |
includes(v) |
❌ | boolean | uses SameValueZero (finds NaN) |
indexOf/lastIndexOf |
❌ | index | uses === (won't find NaN) |
join(sep) |
❌ | string | |
at(i) 🟢 |
❌ | item | supports negatives: arr.at(-1) |
keys/values/entries |
❌ | iterator | |
toSorted/toReversed/toSpliced/with 🟢 |
❌ | new array | immutable versions (ES2023) |
[3, 12, 2].sort(); // [12, 2, 3] ⚠️ string sort!
[3, 12, 2].sort((a, b) => a - b); // [2, 3, 12] ✅ numeric
[1, [2, [3]]].flat(Infinity); // [1, 2, 3]
["a", "b"].at(-1); // "b"
const sorted = arr.toSorted((a,b)=>a-b); // original arr untouched 🟢
arr.with(0, 99); // copy with index 0 replaced
reduce deeply#
// sum
[1,2,3].reduce((acc, n) => acc + n, 0); // 6
// group
["a","b","a"].reduce((m, k) => (m[k]=(m[k]||0)+1, m), {}); // {a:2, b:1}
// pipe (function composition)
const run = (x, fns) => fns.reduce((v, f) => f(v), x);
⚠️ Always pass an initial value; without it, an empty array throws and the first element becomes the accumulator.
Creating & copying#
Array.of(7); // [7] (vs Array(7) → 7 empty slots)
Array.from("abc"); // ["a","b","c"]
Array.from({length:3}, (_, i) => i); // [0,1,2]
[...new Set([1,1,2])]; // [1,2] dedupe
await Array.fromAsync(asyncIterable); // 🟢 ES2024
Holes & sparse arrays ⚠️#
const s = [1, , 3]; // hole at index 1
s.length; // 3
s.forEach(x => {}); // skips the hole
s.map(x => 0); // [0, <hole>, 0] — preserves holes
s.indexOf(undefined); // -1 (holes aren't `undefined`)
Time complexity 🎯#
| Operation | Complexity |
|---|---|
Index access arr[i] |
O(1) |
push/pop |
O(1) amortized |
shift/unshift |
O(n) (reindex) |
splice (middle) |
O(n) |
search indexOf/includes/find |
O(n) |
sort |
O(n log n) |
concat/slice/spread copy |
O(n) |
For frequent front insertion, a plain array's unshift is O(n); consider a different structure or push+reverse.
Interview questions (Part 11):
- Which array methods mutate vs return new? Name the immutable ES2023 additions.
- Why does
[10,9,100].sort()give[10,100,9]? Fix it. - Implement
map,filter,reduceyourself. - Difference between
sliceandsplice;findvsfilter;somevsevery.