Parameters vs Arguments
Two words that get mixed up constantly. A parameter is the name in the function definition. An argument is the value you pass when calling. Same idea as in Python and most other languages:
a and b are parameters. 2 and 3 are arguments. JavaScript binds them positionally — first argument to first parameter, and so on. The distinction is small, but it's the vocabulary error messages and MDN use.
JavaScript Is Loose About Arity
Unlike many languages, JavaScript doesn't care if you pass too few or too many arguments. Missing parameters become undefined. Extra ones are silently ignored:
The first call prints Hello, Ada undefined — last got no value, so it's undefined, and template literals happily interpolate that. No error, no warning. This leniency is sometimes useful and sometimes the source of bugs, which is exactly why default parameters exist.
Setting a Default Value
Put = and a value after the parameter name. If the caller doesn't pass that argument (or passes undefined), the default kicks in:
All three calls work. The first and third trigger the default; the second uses the passed value. This is ES6 syntax — before 2015, you had to write name = name || "friend" inside the body, which had its own bugs around falsy values like 0 and "".
Defaults can be any expression, not just literals:
The expression is evaluated every call, not once when the function is defined. So no mutable-default trap like Python has — each call gets a fresh new Date().
Only undefined Triggers the Default
This is the rule that surprises people. Defaults fire when the argument is undefined, not when it's falsy, and not when it's null:
Only the last call uses "friend". Passing null explicitly means you're saying "the value is null" — JavaScript takes you at your word. Same for empty strings and zeros: they're values, not missing arguments.
If you want to treat null the same as missing, you have to handle it yourself:
The ?? operator (nullish coalescing) treats both null and undefined as "missing." More on that in a later chapter.
Defaults Can Reference Earlier Parameters
Parameters are evaluated left to right, so a later default can use any parameter that came before it:
A call with one argument produces a cube. Two arguments gives a square prism. The forward direction matters — you can't reference a parameter that hasn't been declared yet:
function bad(a = b, b = 1) {
return a + b;
}
bad(); // ReferenceError: Cannot access 'b' before initialization
Same rules as variables declared with let: use before declare is an error.
Defaults Interact With Destructuring
You can destructure parameters and give defaults at the same time. This is a common pattern for "options object" arguments:
Two layers of defaults are at work. The inner ones (role = "member", active = true) fill in missing properties. The outer = {} handles the case where the caller passes no argument at all — without it, createUser() would try to destructure undefined and throw.
The pattern looks dense at first, but it's everywhere in modern JavaScript codebases. Once your eye recognises { ... } = {} as "options with defaults," it reads quickly.
Skipping a Middle Argument
JavaScript doesn't have Python-style keyword arguments. To skip a middle parameter and use its default, you pass undefined explicitly:
Passing undefined for prefix keeps the default. It's ugly. If you find yourself writing undefined in calls often, that's a signal to switch to an options object:
Now the caller names what they want to override, and order doesn't matter.
Defaults Don't Count Toward length
A small detail that rarely matters but occasionally confuses. A function's length property reports the number of parameters before the first one with a default:
Libraries that inspect functions (like some testing and DI tools) use length to count "required" parameters. Good to know the rule exists; not worth memorising unless you're writing that kind of tool.
Next: Rest and Spread
Defaults handle the case where you know the parameters in advance. Sometimes you don't — you want a function to accept any number of arguments, or to forward a bag of arguments to another function. That's what ...rest and the spread operator are for, coming up next.
Frequently Asked Questions
How do you set a default parameter value in JavaScript?
Put = and the default value after the parameter name in the function signature: function greet(name = 'friend') { ... }. If the caller passes no value (or passes undefined), the default is used. This is ES6 syntax and works in all modern JavaScript environments.
What's the difference between parameters and arguments?
Parameters are the names in the function definition — function add(a, b) has parameters a and b. Arguments are the actual values passed when calling — add(2, 3) passes arguments 2 and 3. The distinction matters when reading error messages and docs.
Does a default parameter trigger when I pass null?
No. Defaults only fire when the argument is undefined (or missing entirely). Passing null explicitly means 'I'm giving you a value, and the value is null' — the default is skipped. This trips up people coming from languages where null and undefined are the same thing.
Can a default value reference another parameter?
Yes. Parameters are evaluated left to right, so a later parameter's default can use earlier ones: function box(width, height = width). You can also call functions in the default — function log(msg, time = Date.now()) — and the expression runs fresh on every call.