FAQ: Iterators - The .forEach() Method

I do understand how the function .forEach works and everything but my question is this one regarding the callback Function.

const fruits = ['mango', 'papaya', 'pineapple', 'apple'];

fruits.forEach ( fruitsItem => console.log('I want to eat a ' + fruitsItem ));

fruitsItem is the call back function , the syntax is “single-line block” but i do remember that on the functions chapter single-line block it’s different, isn’t suppose to be like this?

Single-line block:

const loveFruits = fruitsItem => console.log('I want to eat a ' + fruitsItem);

forEach. Method + Single-line block (working as a callback function)

fruits.forEach(const loveFruits = fruitsItem => console.log('I want to eat a ' + fruitsItem));

More precisely, it is the parameter of the callback function. Everything in the argument is the callback.

That’s a legitimate concise body function with permitted relaxed syntax. Note that it is a global object.

We cannot declare things in the forEach argument. It must be a function expression or callback reference.

fruits.forEach(loveFruits)
1 Like

Hi! I’m new here and to coding so I hope this isn’t a too stupid question. Here’s my solution, emulating the shorthand arrow syntax given in the exercise:

const fruits = [‘mango’, ‘papaya’, ‘pineapple’, ‘apple’];
// Iterate over fruits below
fruits.forEach(fruit => console.log('I want to eat a ’ + fruit + ‘.’));

My quandry is I suppose a syntactical one: How does the computer know that my arbitrarily declared variable “fruit” is assigned to the items in the array? Is there an implied assignment due to the syntax of the function, and if so, where specifically in the code would that be?

Thanks!

the .forEach method calls your callback function. fruit is a parameter, so forEach will provide the arguments.

to challenge yourself, you could attempt to implement your own higher order function :slight_smile:

thanks for your answer and suggestion. I’m still wondering where the assignment for the variable is taking place with the concise body function syntax…

in simplest form, this is very likely something like this:

for (let i = 0; i < myArray.length; i++)
{
   callback(myArray[i])
}

But then slightly more sophisticated.

1 Like

How is this `
different from this ’
? Was not sure of the names of them, and confused how the code treated them differently and why

` is called grave accent or backtick. ' is named apostrophe. You can search these symbols on google to get there names

anyway, the template literal was introduced as a new feature in 2015, to prevent breaking change/incompatibility issues the string was enclosed in a different symbol. Why they choice the grave accent for this? Not sure, you would have to do some research

I certainly think the template literals are an improvement compared to how inserting variable in a string was done before. And template literals are faster as well I believe

1 Like

So, I’ve been trying to modify this so it uses the correct article for fruits starting with a vowel and came upon an interesting problem:

const fruits = ['mango', 'papaya', 'pineapple', 'apple', 'orange'];

// Iterate over fruits below

fruits.forEach(fruit => 
{
  const vowels = ["a", "e", "i", "o", "u"];
  for (let i = 0; i < vowels.length; i++)
  {
    if (fruit[0] === vowels[i])
    {
      console.log("I want to eat an", fruit + ".");
      break;
    } else
    {
      console.log("I want to eat a", fruit + ".");
      break;
    }
  }
});

This is printing:

I want to eat a mango.
I want to eat a papaya.
I want to eat a pineapple.
I want to eat an apple.
I want to eat a orange.

Which means it is breaking out of the nested for loop as soon as it sees its not an ‘a’, before iterating through the other vowels.

However if I remove the lower break; it then prints:

I want to eat a mango.
I want to eat a mango.
I want to eat a mango.
I want to eat a mango.
I want to eat a mango.
I want to eat a papaya.
I want to eat a papaya.
I want to eat a papaya.
I want to eat a papaya.
I want to eat a papaya.
I want to eat a pineapple.
I want to eat a pineapple.
I want to eat a pineapple.
I want to eat a pineapple.
I want to eat a pineapple.
I want to eat an apple.
I want to eat a orange.
I want to eat a orange.
I want to eat a orange.
I want to eat an orange.

I know it’s probably a very simple answer, but I just can’t figure out a way to make this work with this particular setup.

if I just move the second console.log to outside the if statement, it then prints

I want to eat a mango.
I want to eat a papaya.
I want to eat a pineapple.
I want to eat an apple.
I want to eat a apple.
I want to eat an orange.
I want to eat a orange.

Edit: the following worked, but had to give up on the elegance of using an array of vowels, to instead use a very long winded and ugly if statement:

fruits.forEach(fruit => 
{
  if ((fruit[0] === "a") || (fruit[0] === "e") || (fruit[0] === "i") || (fruit[0] === "o") || (fruit[0] === "u"))
  {
    console.log("I want to eat an", fruit + ".");
  } else
  {
    console.log("I want to eat a", fruit + ".");
  }
});

Is there a way of using this with a vowel array without running into those issues?

you could use includes:

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/includes

to shorten your if condition. But conditional (if) is the right way to go, not for loop

you could also implement your own function which works similar to include if you like a challenge

1 Like

You mention array; could we not achieve the same net effect using a string object? It is after all, iterable.

Array.forEach() is iterating the fruits array. What if we iterate a vowel string with another iterator (besides using for and if)? This unit describes one such iterator, as mentioned above by @stetim94.

Below we implement the method on a string of vowels and define it as the conditional of a ternary expression which produces one of two possible outputs, 'an' or 'a'. This is all written in an interpolation expression of the template literal which string is the argument for console.log().

String.includes()
fruits.forEach(fruit => {
  console.log(
    `I want to eat ${`aeiou`.includes(fruit.charAt(0)) ? `an` : `a`} ${fruit}.`
  )
})
I want to eat a mango.
I want to eat a papaya.
I want to eat a pineapple.
I want to eat an apple.
I want to eat an orange.

Below is a sneak peek of another possible approach you will learn about in the unit on Regular Expressions. Definitely do not use this in your exercise, but when you reach that unit come back to this…

RegExpr.test()
fruits.forEach(fruit => {
  console.log(
    `I want to eat ${/^[aeiou]+/.test(fruit) ? `an` : `a`} ${fruit}.`
  )
})
I want to eat a mango.
I want to eat a papaya.
I want to eat a pineapple.
I want to eat an apple.
I want to eat an orange.
1 Like