forEach: Iterating for side effects.
The forEach
method in JavaScript provides a clean and readable way to iterate over an array. It executes a provided function once for each array element, primarily used for its side effects, like modifying external variables, logging to the console, or updating the UI, rather than for creating a new array.
Example 1: Basic Usage
const fruits = ['apple', 'banana', 'cherry'];
// Iterate over the array and log each fruit to the console.
fruits.forEach(fruit => {
console.log(fruit);
});
Explanation This code defines an array of strings called fruits
. The forEach
method is then called on this array, and for each element, it executes the arrow function which logs the element to the console.
Example 2: Accessing Index and Array
const colors = ['red', 'green', 'blue'];
// Display each color along with its index.
colors.forEach((color, index) => {
console.log(`Color at index ${index} is ${color}`);
});
Explanation The function passed to forEach
can accept two additional arguments: the index of the current element and the array forEach
was called upon. This example demonstrates accessing and using the index of each element during iteration.
Example 3: Modifying an External Variable
let sum = 0;
const numbers = [1, 2, 3, 4, 5];
// Calculate the sum of the numbers in the array.
numbers.forEach(number => {
sum += number;
});
console.log(sum); // Output: 15
Explanation This example showcases a common side effect: modifying a variable outside the forEach
loop. The function adds each number from the numbers
array to the sum
variable, effectively calculating the total.
Example 4: Working with an Array of Objects
const users = [
{ id: 1, name: 'Alice' },
{ id: 2, name: 'Bob' },
{ id: 3, name: 'Charlie' }
];
// Log a greeting for each user.
users.forEach(user => {
console.log(`Hello, ${user.name}!`);
});
Explanation forEach
is particularly useful for iterating over arrays of objects. In this snippet, we access the name
property of each user
object to print a personalized greeting.
Example 5: Updating Object Properties
const products = [
{ name: 'Laptop', price: 1000 },
{ name: 'Mouse', price: 25 },
{ name: 'Keyboard', price: 75 }
];
// Apply a 10% discount to each product.
products.forEach(product => {
product.price = product.price * 0.9;
});
console.log(products);
Explanation Here, forEach
is used to modify the objects directly within the array. It accesses the price
of each product
and updates it, demonstrating how to perform in-place modifications on array elements.
Example 6: Using thisArg
class Counter {
constructor() {
this.count = 0;
}
incrementBy(numbers) {
// Use the second argument of forEach to set the value of 'this'.
numbers.forEach(function(number) {
this.count += number;
}, this);
}
}
const myCounter = new Counter();
myCounter.incrementBy([5, 10, 15]);
console.log(myCounter.count); // Output: 30
Explanation The forEach
method can optionally accept a second argument, thisArg
, which sets the value of this
inside the callback function. This is useful in older JavaScript or specific design patterns for maintaining the correct context.
Example 7: Asynchronous Operations
const urls = ['/api/data1', '/api/data2'];
// Note: forEach does not wait for async operations to complete.
async function fetchData(url) {
console.log(`Fetching data from ${url}`);
// In a real scenario, you would use fetch() here.
return new Promise(resolve => setTimeout(() => resolve(`Data from ${url}`), 100));
}
urls.forEach(async (url) => {
const data = await fetchData(url);
console.log(data); // This logging happens asynchronously.
});
console.log('Fetching initiated.');
Explanation While you can use async/await
within a forEach
callback, the forEach
loop itself will not wait for these asynchronous operations to complete before moving on. This example shows that "Fetching initiated." is logged first, and the fetched data logs appear later as each promise resolves. For sequential asynchronous operations, consider using a for...of
loop.