Functions
The Problem Functions Solve
Imagine you need to calculate the area of a circle in five different places in your program. Without functions, you write the formula five times:
This works. But it has a serious problem. If you discover you should use Math.PI instead of 3.14159, you must find and fix every single line. If you have 50 places — you fix 50 lines. If you miss one — you have a bug.
The deeper problem: your code doesn't say what it's doing. A reader sees 3.14159 * r1 * r1 and must figure out that it's an area calculation. That's mental work you are forcing on every future reader — including yourself.
Functions solve both problems at once.
Defining a Function
Now the formula exists in exactly one place. The name circleArea says exactly what it does. If the formula ever needs to change, you change it once.
The structure:
function name(parameters) {
// body: instructions
return value;
}
function— keyword that creates a function- name — what you call it; same naming rules as variables
- parameters — the inputs the function expects, listed inside
() - body — the instructions that run when the function is called
return— the output the function sends back
Parameters and Arguments
Parameters are the placeholders defined when you write the function. Arguments are the actual values you pass when you call it.
name and timeOfDay are parameters — they are just local labels that exist inside the function. When you call greet("Sanjib", "morning"), the value "Sanjib" is assigned to name and "morning" to timeOfDay for the duration of that one call.
Return Values
return does two things simultaneously: it sends a value back to wherever the function was called, and it immediately stops the function. No code after return runs.
A function without a return statement (or with a bare return;) returns undefined.
The function does something (prints), but it doesn't produce a value. This distinction between doing and producing is fundamental — you will think about it for the rest of your programming life.
Default Parameters
What if a caller doesn't pass an argument? The parameter becomes undefined. You can set a default to handle this gracefully:
Default parameters are evaluated only when the argument is missing or undefined. They make functions more forgiving without making them less precise.
Scope — The Invisible Boundary
Variables declared inside a function exist only inside that function. They are invisible to the outside world. This boundary is called scope.
The error is not a bug — it is the system working correctly. Scope means that functions are self-contained. A variable named result inside one function cannot accidentally interfere with a variable named result inside another. Without scope, every variable name in your entire program would have to be unique, and programs of any size would become impossible to manage.
Two functions, both using x, zero interference. This is why scope is a feature, not a restriction.
Functions can see variables declared outside them — but that's a more advanced topic involving closures, which gets its own dedicated lesson later.
Functions Are Values
Here is the idea that separates JavaScript from many other languages: a function is just another value. Like a number or a string, you can store a function in a variable, pass it to another function, or return it from a function.
This is called a function expression — instead of declaring a function with a name, you create it and assign it to a variable. The function itself has no name; the variable square is just a label pointing to it.
This might seem like a strange way to write a function. Its power becomes clear in the next section.
Arrow Functions
ES6 introduced a shorter syntax for function expressions: the arrow function.
The concise form n => n * n * 4 means: "take n, evaluate n _ n _ 4, return it." No braces, no return keyword needed — the expression after => is the return value implicitly.
Arrow functions are everywhere in modern JavaScript. You will see them constantly. The rule is simple:
- One parameter → parentheses optional:
n => n * 2 - Multiple parameters → parentheses required:
(a, b) => a + b - No parameters → empty parentheses required:
() => 42
Passing Functions to Functions
Because functions are values, you can pass one function as an argument to another. This is one of the most powerful ideas in all of programming.
applyTwice doesn't know or care what fn does. It just calls it twice. You can pass any function and applyTwice will work correctly. This is the foundation of functional programming — a style you will explore deeply in later lessons.
A Function That Builds Functions
Functions can also return functions. This unlocks a technique called closures — one of JavaScript's most powerful and most misunderstood features. Here is a first glimpse:
makeMultiplier(2) returns a new function that remembers factor = 2. That returned function is stored in double. When you call double(5), it uses the factor it memorised. The returned function closed over the variable factor — that's a closure.
Don't worry if this feels mysterious. It will get its own full lesson. For now, just notice that it works — and that it's elegant.
Pure Functions
A pure function is one that:
- Given the same inputs, always returns the same output
- Has no side effects — it doesn't change anything outside itself
Pure functions are predictable, testable, and safe to reuse anywhere. Impure functions are sometimes necessary — but you should know when a function is impure and have a reason for it.
As you grow as a programmer, you will instinctively reach for pure functions first.
What You Have Learned
Functions are how you give names to ideas, eliminate repetition, and build programs out of composable pieces.
The key ideas:
- A function packages instructions under a name; define once, use anywhere
- Parameters are inputs;
returnis the output — doing vs producing - Variables inside a function are invisible outside — scope is a feature
- Functions are values: store them, pass them, return them
- Arrow functions
(params) => expressionare the modern short form - A function that returns a function creates a closure — more on this soon
- Prefer pure functions: same input always gives same output, no side effects
In the next lesson: Loops — how to make the computer do the same thing many times without writing it many times. Combined with functions, loops are where programs start to feel genuinely powerful.