How to iterate elements with forEach in Dart

In Dart programming language, the forEach method is a way to iterate over the elements in an iterable collection, such as a list, map, or set. This method allows for the execution of a given function on each element in the collection without the need for an explicit loop.

The significance of forEach in Dart programming lies in its simplicity and versatility. It is a concise and straightforward method that can be used to perform a variety of actions on elements in a collection.

The forEach method takes a single parameter—a function applied to each element in the collection. The function takes one argument, which is the current element being processed. The syntax for the forEach method is as follows:

iterable.forEach((element) { ... });
  • The forEach method is used to iterate over elements in a collection (represented by the iterable).

  • The method takes an anonymous function as its argument, which is defined at the point of call.

  • The anonymous function takes one argument, element, which represents the current element being processed from the iterable object.

  • The body of the anonymous function, defined within the curly braces { ... }, contains the action that will be performed on each element as it is processed from the iterable object.

Use cases of the forEach loop

The forEach loop is one of several methods available in Dart for iterating over elements in a collection. It is important to understand when it is more appropriate to use forEach compared to other iteration methods like map and where.

The map method is used to transform each element in a collection into a new value, returning a new collection with the transformed values. The where method is used to filter elements in a collection based on a specified condition, returning a new collection with only the elements that satisfy the condition.

The forEach loop is more appropriate when the goal is to perform an action on each element in a collection, rather than transforming or filtering the elements. For example, we might use forEach to print each element in a list, or to increment a counter for each element in a set.

Examples with different data structures

To better understand the use of forEach in Dart, it is helpful to look at examples with different data structures. Here're examples of using forEach with a list, set, and map:

void main() {
List<String> names = ['Ayo', 'David', 'Victoria', 'Helen'];
names.forEach((name) {
print(name);
});
}

Explanation

  • Line 2: We define a list of strings as names with 4 elements.

  • Lines 3–5: We call the forEach method on the names list, passing an anonymous function as an argument. The anonymous function takes a single argument name which represents the current element being processed from the names list, and has a single statement: print(name) which prints the name argument to the console.

Example

void main() {
Set<int> numbers = {1, 2, 3};
numbers.forEach((number) {
print(number);
});
}

Explanation

  • Line 2: We define a set of integers as numbers with the values 11, 22, 33.

  • Lines 3–5: We call the forEach method on the numbers set, passing an anonymous function as an argument. The anonymous function takes a single argument number which represents the current element being processed from the numbers set, and has a single statement: print(number) which prints the number argument to the console.

Example

void main() {
Map<String, int> ages = {'Ayo': 30, 'Samuel': 25, 'Emmanuel': 35};
ages.forEach((name, age) {
print('$name is $age years old');
});
}

Explanation

  • Line 2: We define a map as ages with key-value pairs 'Ayo': 30, 'Samuel': 25, 'Emmanuel': 35.

  • Lines 3–5: We call the forEach method on the ages map, passing an anonymous function as an argument. The anonymous function takes two arguments name and age, which represents the current key and value being processed from the ages map respectively, and has a single statement: print('$name is $age years old') which prints the name and age arguments to the console.

Example

void main() {
List<Map<String, int>> grades = [
{'Ayo': 60, 'Samuel': 89, 'Vic': 70},
{'Ayo': 58, 'Samuel': 78, 'Vic': 58},
{'Ayo': 86, 'Samuel': 70, 'Vic': 99}
];
int sum = 0;
grades.forEach((studentGrades) {
studentGrades.forEach((student, grade) {
sum += grade;
});
});
print('The sum of all grades is $sum');
}

Explanation

  • Lines 2–6: We define a list of maps as grades, where each map represents a set of student names as keys and their respective grades as values.

  • Lines 8–13: We initialize the variable named sum to 00, then we use the forEach method to loop through the list of maps, where each map is represented by the variable studentGrades. Within the inner forEach, each key-value pair within studentGrades is accessed, and the value is added to the sum variable.

  • Line 15: The sum of all grades is printed to the console.

Note: Avoid nested loops for better performance as it can slow down the code in worst case scenarios

Best practices and pitfalls to avoid

Maximize the use of forEach by following these best practices and avoiding these common pitfalls for optimal performance and efficiency.

Best practices

  • Use forEach when we need to perform simple operations on each element in the iterable, such as printing or counting.

  • Choose the right iterable type (e.g. List, Set, Map) based on the operations we need to perform

Pitfalls to avoid

  • Avoid using nested loops as it can lead to performance issues and slow down the processing time.

  • forEach does not allow us to modify the iterable we are working on, so we'll use other methods such as map or where to modify the data, if required.

Free Resources