Function Declaration vs Function Expression: What's the Difference?

Same job. Different behavior. One gotcha that trips up every beginner exactly once.
1. What Are Functions and Why Do We Need Them?
Imagine you need to calculate a discount for 50 different products. Without functions, you'd copy-paste the same math 50 times. Change the logic once? Update it in 50 places. That's a nightmare.
Functions fix this. You write the logic once, give it a name, and call it wherever you need it.
function applyDiscount(price) {
return price * 0.9; // 10% off
}
applyDiscount(500); // 450
applyDiscount(1200); // 1080
applyDiscount(80); // 72
Same logic. Three calls. Zero repetition. That's the power of functions — reusable blocks of code.
2. Function Declaration
A function declaration is the classic, most familiar way to define a function. You use the function keyword followed by a name.
function greet(name) {
return "Hello, " + name + "!";
}
console.log(greet("Niti")); // Hello, Niti!
Syntax breakdown:
function greetUser (name) { ... }
↑ ↑ ↑
keyword name parameters
Clean. Readable. Named. This is what most beginners start with, and it works exactly as you'd expect.
3. Function Expression
A function expression stores a function inside a variable. Instead of declaring the function standalone, you assign it like a value.
const greet = function(name) {
return "Hello, " + name + "!";
};
console.log(greet("Niti")); // Hello, Niti!
Same output. Different structure. The function itself has no name — it's anonymous and lives inside the variable greet.
You can also name it (called a named function expression), which helps with debugging:
const greet = function greetFn(name) {
return "Hello, " + name + "!";
};
The name greetFn is only accessible inside the function itself — from the outside, you still call it as greet().
4. Key Differences: Declaration vs Expression
On the surface they look similar. Under the hood, they behave very differently — especially when it comes to whenyou can call them.
Syntax comparison:
// Function Declaration
function multiply(a, b) {
return a * b;
}
// Function Expression
const multiply = function(a, b) {
return a * b;
};
The biggest difference — hoisting:
// ✅ This works — declaration is hoisted
console.log(add(2, 3)); // 5
function add(a, b) {
return a + b;
}
// ❌ This breaks — expression is NOT hoisted
console.log(subtract(5, 3)); // TypeError: subtract is not a function
const subtract = function(a, b) {
return a - b;
};
Function declarations can be called before they appear in the code. Function expressions cannot.
This is because of something called hoisting — and it's one of the most important concepts to understand early.
5. Hoisting (The Simple Version)
When JavaScript runs your file, it does a quick scan before executing anything. During this scan, it picks up all function declarations and moves them to the top (mentally — not literally in your file).
Think of it like this: JavaScript reads your entire script, sees all the function declarations, and says "okay, I know about these already" before running a single line.
// JavaScript mentally does this:
// ─── HOISTED TO TOP ───
// function greet(name) { return "Hello, " + name; }
// ──────────────────────
greet("Niti"); // Works! Already known.
function greet(name) {
return "Hello, " + name;
}
Function expressions don't get this treatment. The variable (const greet) is technically hoisted, but its value (the function) isn't assigned yet. So calling it early gives you an error.
sayHi(); // ❌ ReferenceError or TypeError — value not assigned yet
const sayHi = function() {
return "Hi!";
};
One-line rule: Declarations are hoisted with their value. Expressions are not.
6. When to Use Each
Both are valid. Choosing between them comes down to your situation.
Use a function declaration when:
You want the function available everywhere in its scope
You're defining utility functions that get called frequently
Readability and discoverability matter (named functions are easier to scan)
function calculateTax(price, rate) {
return price * (rate / 100);
}
Use a function expression when:
You're passing a function as an argument (callbacks)
You want to conditionally define a function
You want the function to only be available after its definition
const double = function(n) { return n * 2; };
const numbers = [1, 2, 3, 4];
const doubled = numbers.map(double); // [2, 4, 6, 8]
As a beginner, start with declarations. Once you're comfortable, expressions will feel natural — especially when you hit callbacks and array methods.
7. Putting It All Together (Assignment)
// 1. Function Declaration that multiplies two numbers
function multiply(a, b) {
return a * b;
}
// 2. Same logic as a Function Expression
const multiplyExpr = function(a, b) {
return a * b;
};
// 3. Call both and print results
console.log(multiply(4, 5)); // 20
console.log(multiplyExpr(4, 5)); // 20
// 4. Try calling before defining — observe the difference
// ✅ Declaration called BEFORE its definition — works!
console.log(multiplyEarly(3, 6)); // 18
function multiplyEarly(a, b) {
return a * b;
}
// ❌ Expression called BEFORE its definition — breaks!
console.log(multiplyLate(3, 6)); // TypeError: multiplyLate is not a function
const multiplyLate = function(a, b) {
return a * b;
};
What you'll observe: The declaration runs fine even before the code defines it. The expression throws an error. This is hoisting in action — and now you've seen it firsthand.
Quick Recap
A function declaration uses
function name() {}and is hoisted — call it anywhereA function expression stores a function in a variable — must be defined before calling
Both do the same job; the difference is when and where you can use them
Prefer declarations for utility/reusable logic, expressions for callbacks and scoped use
Once this distinction clicks, a whole lot of JavaScript weirdness starts making sense.
Questions? Drop them below. Happy coding! 🚀




