Skip to main content
CodeFlow
functions~14 minRoute 01 10 of 12

Higher-Order Functions

Functions that take or return other functions — map, filter, reduce, and friends.

Prerequisites:FunctionsArrays & Lists

Story — three workers on a conveyor belt

Imagine a conveyor belt of items. Three workers stand beside it. One transforms each item as it goes by. The next filters — anything that fails the test goes in the bin. The third reduces — squashing whatever's left into a single result, like a running total.

That's map, filter, and reduce. They're higher-order functions — functions that take other functions as arguments. The work each station does is whatever function you hand it. The shape of the pipeline stays the same; the meaning shifts with the lambdas.

Mapa says

A loop says how: for each i, do step. A pipeline says what: from this list, keep evens, double them, sum. Sometimes the loop wins. Sometimes the pipeline does. Read both; choose by clarity.

See it — three patterns cover most loop code

Almost any "walk a list and build something" loop fits one of three shapes. map: same number of items, transformed. filter: fewer items, same shape. reduce: one accumulated result. Once you see the shape, the right tool jumps out.

✎ Sharpen your pencil

Write one sentence describing what map and filter have in common — and one thing only filter does.

Mapa says

map transforms each item; filter keeps some; reduce squashes everything into one. Three patterns cover most loop-and-build code.

Try it — pick the right tool

Exercise. Match each task to map / filter / reduce:

  • (a) Convert a list of celsius temps to fahrenheit
  • (b) Find the maximum of a list of numbers
  • (c) Drop all the negative numbers from a list
Reveal answer

(a) map — same number of values, each transformed. (b) reduce — collapse all values to one. (c) filter — keep some, drop others, no change to kept values.

Code it — five languages, one pipeline

Python and JavaScript are the most natural fits. Java needs streams. C++ has standard algorithms but they're verbose. Go intentionally omits them — explicit loops are the idiom.

nums = [1, 2, 3, 4, 5]

# map: transform each
doubled = list(map(lambda x: x * 2, nums))   # [2, 4, 6, 8, 10]

# filter: keep some
evens = list(filter(lambda x: x % 2 == 0, nums))  # [2, 4]

# reduce: squash to one
from functools import reduce
total = reduce(lambda a, b: a + b, nums)     # 15

# Pythonic: list comprehensions cover map+filter
doubled = [x * 2 for x in nums]
evens = [x for x in nums if x % 2 == 0]

Quiz it — make it stick

  1. Question 1

    What is a `pure` function?

  2. Predict — Question 2

    What does this JavaScript print?

    const result = [1, 2, 3, 4]
      .filter(x => x > 1)
      .map(x => x * 10)
      .reduce((a, b) => a + b, 0);
    console.log(result);
  3. True or false — Question 3

    reduce can express any computation that map and filter can — but not vice versa.

No Dumb Questions

Real questions other learners asked on this page.

  • Why call them "higher-order"?
    Because they operate on functions — taking a function as input or returning one as output. A "first-order" function only takes data. The label comes from logic, not from hierarchy.
  • What is a pure function?
    One whose output depends only on its inputs and that has no side effects (no printing, no mutating globals, no calling APIs). Pure functions are easy to test, cache, and reason about. Most useful programs aren't pure end-to-end — but isolating purity is a powerful design tool.
  • Is reduce always the right choice when I want to fold a list?
    It works, but a comprehension or built-in often reads better. Use reduce when you genuinely need a running accumulator (running totals, grouping, stateful folds). For simple sums or maxes, sum() and max() exist for a reason.