Currying transforms a function with multiple arguments into a sequence of single-argument functions, while partial application fixes some arguments upfront and returns a function expecting the rest.
Transforms f(a, b, c) into f(a)(b)(c) — a chain of unary functions where each call returns the next function until all arguments are supplied.
Fixes some arguments upfront and returns a function expecting the rest — JavaScript's bind() provides built-in partial application.
Currying always produces unary functions in a chain; partial application fixes any number of arguments at once and returns one function.
Configuration functions, event handlers with preset context, reusable validators, and function composition pipelines.
Both patterns capture fixed arguments in closures — each returned function remembers previously supplied arguments across calls.
Currying and partial application are two related techniques from functional programming that transform functions to make them more reusable and composable. Both rely on closures to remember previously supplied arguments.
Currying transforms a function that takes multiple arguments into a sequence of functions that each take a single argument. A curried version of f(a, b, c) becomes f(a)(b)(c) — each call returns a new function that expects the next argument, until all arguments are supplied and the result is computed.
Basic implementation:
function curry(fn) {
return function curried(...args) {
if (args.length >= fn.length) return fn(...args);
return (...moreArgs) => curried(...args, ...moreArgs);
};
}This generic curry wrapper checks fn.length (the number of declared parameters). If enough arguments are provided, it calls the original function. Otherwise, it returns a new function that accumulates more arguments via closure.
Partial application fixes one or more arguments of a function upfront and returns a new function that accepts the remaining arguments. Unlike currying, it doesn't require unary functions — you can fix any number of arguments at once.
JavaScript has built-in partial application via Function.prototype.bind(): const double = multiply.bind(null, 2) fixes the first argument to 2. You can also implement it manually with closures: const partial = (fn, ...fixed) => (...rest) => fn(...fixed, ...rest).
Currying always produces a chain of unary (single-argument) functions — f(a)(b)(c). Partial application fixes a specific set of arguments and returns one function that takes the rest — f(a, b) with first arg fixed becomes g(b). Currying is a specific form of transformation; partial application is a more general concept. A curried function can be partially applied by calling it with fewer arguments than it needs.
Configuration functions: Create a base function with shared settings, then specialize it. const apiCall = curry((baseUrl, endpoint, params) => fetch(baseUrl + endpoint, params)). Then const myApi = apiCall('https://api.example.com') creates a pre-configured function.
Event handlers: const handleClick = curry((action, elementId, event) => { ... }). Pre-fill the action and element, pass the resulting function directly to addEventListener.
Validation: const isInRange = curry((min, max, value) => value >= min && value <= max). Create const isValidAge = isInRange(0, 120) — a reusable validator.
Function composition: Curried functions compose naturally. const pipeline = compose(format, validate, parse) — each function in the pipeline takes one argument and returns one result.
Both patterns fundamentally depend on closures. When a curried function receives its first argument, that argument is captured in the closure of the returned function. Each subsequent call creates a new closure that captures the next argument while retaining access to all previous arguments.
Currying transforms a multi-argument function into a chain of single-argument functions. Partial application fixes some arguments and returns a function for the rest. bind() provides built-in partial application in JavaScript. Both patterns enable function reuse and composition, and both rely on closures to remember fixed arguments.
Fun Fact
Currying is named after mathematician Haskell Curry (who also gave his name to the Haskell programming language). Ironically, the concept was first described by Moses Schönfinkel in 1924 — Curry merely popularized it. In Haskell, all functions are automatically curried by default.