In any moderately complex JavaScript program, everything happens inside functions.
Functions are a core, essential part of JavaScript.
A function is a series of code statements combined together in a single block and given a name.
The code in the block can then be executed by referencing that name.
Defining Functions
Functions are defined using the function keyword followed by a name that describes the use of the function, a list of zero or more arguments in (), and a block of one or more code statements in {}.
function functionName() {
// code to be executed
}
Function Example
Here's a simple function that displays a greeting:
function sayHello() {
console.log("Hello, World!");
}
// Call the function
sayHello(); // Outputs: Hello, World!
Function Parameters
Functions can accept parameters (also called arguments) that allow you to pass data into the function:
function greet(name) {
console.log("Hello, " + name + "!");
}
greet("Alice"); // Outputs: Hello, Alice!
greet("Bob"); // Outputs: Hello, Bob!
You can also have multiple parameters:
function add(a, b) {
return a + b;
}
console.log(add(5, 3)); // Outputs: 8
console.log(add(10, 20)); // Outputs: 30
Return Values
Functions can return values using the return statement. The return statement stops the execution of the function and returns a value to the caller.
function multiply(a, b) {
return a * b;
}
let result = multiply(4, 5);
console.log(result); // Outputs: 20
If a function doesn't have a return statement, it returns undefined:
function doSomething() {
console.log("Doing something...");
}
let result = doSomething();
console.log(result); // Outputs: undefined
Function Expressions
You can also define functions using function expressions. These are anonymous functions assigned to variables:
const greet = function(name) {
return "Hello, " + name + "!";
};
console.log(greet("Alice")); // Outputs: Hello, Alice!
Arrow Functions
Arrow functions provide a shorter syntax for writing function expressions:
// Regular function expression
const add = function(a, b) {
return a + b;
};
// Arrow function
const addArrow = (a, b) => {
return a + b;
};
// Even shorter arrow function (implicit return)
const addShort = (a, b) => a + b;
console.log(add(5, 3)); // Outputs: 8
console.log(addArrow(5, 3)); // Outputs: 8
console.log(addShort(5, 3)); // Outputs: 8
For single parameters, you can omit the parentheses:
const square = x => x * x;
console.log(square(5)); // Outputs: 25
Function Scope
Variables declared inside a function are local to that function and cannot be accessed from outside:
function myFunction() {
const localVar = "I'm local";
console.log(localVar); // Outputs: I'm local
}
myFunction();
// console.log(localVar); // Error: localVar is not defined
Functions can access variables declared in their outer scope:
const globalVar = "I'm global";
function showGlobal() {
console.log(globalVar); // Outputs: I'm global
}
showGlobal();
Higher-Order Functions
JavaScript functions can be passed as arguments to other functions and returned as values from functions. Such functions are called higher-order functions.
// Function that takes another function as an argument
function operate(a, b, operation) {
return operation(a, b);
}
function add(a, b) {
return a + b;
}
function multiply(a, b) {
return a * b;
}
console.log(operate(5, 3, add)); // Outputs: 8
console.log(operate(5, 3, multiply)); // Outputs: 15
Built-in Array Methods
JavaScript provides many built-in higher-order functions for working with arrays:
const numbers = [1, 2, 3, 4, 5];
// map: transform each element
const doubled = numbers.map(x => x * 2);
console.log(doubled); // [2, 4, 6, 8, 10]
// filter: keep elements that meet a condition
const evens = numbers.filter(x => x % 2 === 0);
console.log(evens); // [2, 4]
// reduce: reduce array to single value
const sum = numbers.reduce((acc, x) => acc + x, 0);
console.log(sum); // 15
// forEach: execute function for each element
numbers.forEach(x => console.log(x));
Function Best Practices
✓ Do:
- Use descriptive function names
- Keep functions small and focused on one task
- Use arrow functions for short operations
- Document your functions with comments
- Handle edge cases and errors
✗ Don't:
- Create functions that are too long or complex
- Use global variables inside functions
- Forget to return values when expected
- Nest functions too deeply
- Use unclear parameter names
Complete Example
// A more complex example showing multiple concepts
const calculator = {
add: (a, b) => a + b,
subtract: (a, b) => a - b,
multiply: (a, b) => a * b,
divide: (a, b) => {
if (b === 0) {
throw new Error("Cannot divide by zero");
}
return a / b;
}
};
function calculate(operation, a, b) {
if (typeof calculator[operation] === 'function') {
return calculator[operation](a, b);
} else {
throw new Error("Unknown operation: " + operation);
}
}
try {
console.log(calculate('add', 10, 5)); // 15
console.log(calculate('multiply', 4, 6)); // 24
console.log(calculate('divide', 20, 4)); // 5
} catch (error) {
console.error(error.message);
}