Need Help: Functional Programming: Use the map Method to Extract Data from an Array

Hello. I tried the “Ask for help” button on this exercise and got a page that said " 414 Request-URI Too Large". Not sure what that means.

So I’ve successfully used the map method in solving prior code challenges but apparently I don’t have a good enough understanding of it to solve this challenge:

I looked at the hint and it provides an “Intermediate Code Solution.” Can someone explain what an “Intermediate Code Solution” is? Does that mean it’s not the complete solution, but only an intermediate step in solving the challenge? The “Intermediate Code Solution” provides the code below, but I don’t completely understand what the code is doing.

  rating = watchList.map( (item) => ({"title":item["Title"], "rating":item["imdbRating"]}) );

I will explain as much as I understand and what I think I don’t understand then maybe someone can help clarify/explain.

First, the challenge provides this code:
var rating = [];
I’m not sure if this code is necessary, but I think it declares a variable called “rating” and assigns it to an empty array.

Then the solution code provided above then assigns the variable “rating” to the value of the map method that is used (invoked? called?) on the watchList array. I’m still not clear on what a callback function is but I think it’s the function that’s after the arrow => notation. (If anyone can clarify this and explain what we are calling back that would be helpful - I think? Also I’m still trying to figure out the difference between “invoke” and “call” and “callback”).

The map function iterates over every item in the watchList array and does something to each item. Specifically it calls a function that takes one input (parameter “item”) and then does something to each “item” (which I think means each object) in the watchList array.

I understand how the loop function works and that we are trying to do the same thing using the map method.

Did I get that right so far?

I don’t understand the following code:

({"title":item["Title"], "rating":item["imdbRating"]}) );

I’ve reviewed and re-reviewed the MDN explanation of the map method, searched the forums and read the postings about this challenge, googled this particular challenge and also the JS map method, and also searched topics that I thought might be relevant, like how to change an object in an array with the map method. But I still don’t understand the solution so I’m hoping someone can help.

thanks!

it is the whole solution, but at intermediate level of difficulty


map is a method that takes a function as argument, when a function is an argument of an other function it is called callback

the callback of map in this case is this one:

(item) => ( // arrow function with implicit return - the value after the arrow is returned without need of using the return keyword, round parenthesis needed to avoid confusion with graph parenthesis surrounding a function body
   { // opening parenthesis of an object 
      "title": item["Title"], // first property of the object, called "title" with value equal to that of the "Title" property of the starting object
      "rating": item["imdbRating"] // second property of the object, called "rating", with value equal to that of the property "imdbRating" of the starting object
   }  // closing paretnhesis of the object
)

Thanks for the reply. Many more question arise…

Is there also an easier/more difficult solution to this challenge? Just curious why they would call it “intermediate.” Why wouldn’t we want to use the easiest solution, instead of a more difficult (intermediate) solution? I would think that in writing code we would want to use the easiest solution to achieve the desired result.

Regarding callback functions, I guess I’m still looking for an explanation as to why it’s called a “callback” - that maybe if I understood the reasoning for choosing this word, then maybe I would have a better understanding of the logic of callback functions.

My Webster’s Dictionary defines callback as:

*n.

  1. an additional audition as for a theatrical role.
  2. a return telephone call.*

So I’m trying to figure out the significance of the word callback in how it might relate to its standard English meaning.

Do we need the code
var rating = [];
?
I’m thinking that if we have this empty array, don’t we need to use the push method to add elements to this array?

The instructions state “Use map to pull the title and rating from watchList and save the new array in the rating variable.”

But in the solution I see we are adding “title” and “rating” - why are we adding these words? They are not in the original watchList array, so we did not pull them from the original array as per the instructions, we just added them. (I do see “Title” and “imdbRating” in the original array but these are not the same as “title” and “rating”). So adding “title” and “rating” does not comply with the instructions to pull them from the original watchList array.

In the solution we are also using ["Title"] and ["imdbRating"], which are in the original array, but we are adding them into our function, not pulling them from the original array, as the instructions ask us to do. So this solution does not comply with the instructions.

I’m trying to relate the solution to the MDN explanation of the syntax for the map method (is this the same as Array.prototype.map? I’m not sure what prototype means here, so I hope I am looking at the right info):

var new_array = arr.map(function callback(currentValue[, index[, array]]) {
    // Return element for new_array
}[, thisArg])

So I’m thinking the only parameter we are using with the callback function is the currentValue (“item” in the solution), right? I’m still unclear as to why the curly braces (graph parentheses) are there in the solution. I know we need them for an object, but they (curly braces) are already in the original array, so shouldn’t we get them from the original array, instead of writing them all over again?

Thanks again for the help!

you can check this for an article about callbacks:


first, arrow functions

this is a function:

function (x) {
   /* do stuff */
   return /* valueToReturn */
}

with arrow function become like this:

(x) => {
   /* do stuff */
   return /* valueToReturn */
}

if the function has only the return statement like below you can make it even more compact
function with only return:

(x) => {
   return /* valueToReturn */
}

this function can be written with implicit return, and you do this by not using the graph parenthesis that indetify the function body and not using the return keyword
with implicit return you put the value to return immediately to the right of the arrow

(x) => /* valueToReturn */

if there is only one parameter you can also avoid the parenthesis around the parameter if you have more than one parameter you can’t omit them

x => /* valueToReturn */

if you want to return an object with implicit return you need to make sure that the graph parenthesis are not mistaken for those delimiting the function body, so you wrap the value to return in round parenthesis

(x) => ( /* valueToReturn */ ) // in this way you can implicitly return an object without syntax issues 

now, map
let’s say we have a generic callback called func

arr.map(func)

map will return an array where each element is the returned value from the callback when the element at that index in the original array is passed in: [func(arr[0]), func(arr[1]), ... , func(arr[arr.length - 1])]


we don’t need push here, map returns a new array that we are assigning to raring
the best thing would be to do

var rating = watchlist.map(...);

if there was only one solution, then that is what is present in the guide, but there are many possible ways to solve any challenge, some are just syntax variations, others different level of complexity - it could be that it is to make the guide similar to that of other challenges where there are usually 3 level of complexity.
The best solution it is usually the most readable - also, “easy” is subjective, but so is “readable”.
This is something that generate heated discussions.


we are not adding those, we are creating a new object that has only those two properties - the original object has many more properties, so we are actually extracting just those two properties from there.

to write a valid object you need to use the curly brackets, if you don’t use them it is not an object.


an example of a more complex solution, as destructuring can be considered a more advanced topic, but shorter, and someone could say more readable:

var rating = watchList.map(
   ({Title, imdbRating}) => (
      {
         "title": Title,
         "rating": imdbRating
      }
   )
);

Thanks for taking the time to address my questions. Unfortunately I’m even more confused than previously!

Reviewing the FCC info on Callback Functions, I’m not clear on what a “first class object” is. What would be an example of an object that is not a “first class object?” Are there “second” and “third” class objects, for example, and what would they be?

Also, I don’t understand what is meant by ‘to be “called back” at a later time.’ Why is it being “called back,” rather than just “called?” I understand that a higher order function accepts other functions as arguments, but I don’t understand what they mean by ‘higher-order function … contains the logic for when the callback function gets executed.’ Where is the logic that states when it should be executed (I’m assuming that executed means the same thing as call which is the same as invoke which is the same as callback - but I’m not clear on why there are so many different words to refer to the same thing - I find this extremely confusing!).

I think I do understand how arrow functions work, from doing previous exercises and code challenges - thanks for the review.

Regarding the challenge in question, I still am unclear on several things.

First, do we need the code
var rating = [];

Or would it be incorrect to use it in any solution…or is using the above code one option for a solution?

I thought that the map method was iterating over the items in an array in the same way that a loop would - one-by-one. If so, then we should be able to use the push method, just like with a loop, right? Maybe I’m not understanding the map function? I’ve read various explanations several times so I’m not sure what I’m missing.

I do understand that we need the curly braces to write a valid object - but we already have a bunch of valid objects in the original array, so I don’t understand why we wouldn’t just use those objects and take out what we need, instead re-writing the curly braces.

Maybe part of my confusion is the following -

You provided an example of code:

[func(arr[0]), func(arr[1]), ... , func(arr[arr.length - 1])]

and there are no curly braces in the above code!
but the example solution has curly braces.

rating = watchList.map( (item) => ({"title":item["Title"], "rating":item["imdbRating"]}) );

So I’m having trouble getting from the example of the map method (no curly braces anywhere!) to the solution (curly braces!).

The MDN map method “Syntax” also has no curly braces:

var new_array = arr.map(function callback(currentValue[, index[, array]]) {
    // Return element for new_array
}[, thisArg])

While I do understand that objects need curly braces… the examples have no curly braces, only brackets. Where are those curly braces?!

I’m also confused that we have a global variable (watchList) - I thought that in functional programming we were not supposed to use global variables, that everything should be done within the function itself. Maybe I misunderstood that. In functional programming we apparently still have objects, global variables, and functions…so what is the difference between object-oriented and functional programming…

It does make sense that there could be many ways to solve this coding challenge, with different levels of so-called complexity - “so-called” because, as you said, “easy” and “readable” are indeed subjective terms. That’s why I still find it confusing why they would use such a subjective term (“intermediate”) - intermediate compared to what?

Again thanks for taking the time to help. I keep searching and reading stuff over and over but every “answer” I seem to find just generates more questions…

you need to look at other languages for an example of this


in the definition of the method, which for these methods is already present in the language.
here two challenges in which you need to write the logic of the methods yourself:
https://learn.freecodecamp.org/javascript-algorithms-and-data-structures/functional-programming/implement-the-filter-method-on-a-prototype
https://learn.freecodecamp.org/javascript-algorithms-and-data-structures/functional-programming/implement-map-on-a-prototype

it is confusing, but that’s how anything is, many ways to say the same thing, often with subtle differences


you don’t need it, because you can directly assign the returned value from map, but you can use it


yes, it iterates over the array, do something with the array elements and return a new array with the changed elements. if you were to use map to push elements inside an other array that’s misusing the resources you have. don’t worry, if you want to use a method to iterate over an array, without any other feature, you can use forEach


I am calling a function passing in an argument. you have never used curly braces there, have you?
that each function call is an element inside an array doesn’t make the curly braces needed.

and how would you do that?
you can reference the object, and reference each property value, but you can’t create the new object you need to return it you don’t use the curly braces…

yes, it is writing an object. an object can be a value like anything else. maybe the examples use numbers, or just placeholders, well, here it returns an object.

I don’t understand where you want them… the function returns a value, that value can be anything, you need curly braces only if you return an object, because that’s how an object is made


maybe it’s time you dedicate some time to reading a javascript book or two…
two suggestions that are free and immediately available:

Thanks again for taking the time to respond to all my questions. Still confused but I’ll keep trying.

You had previously mentioned these JavaScript books. I did find them and I took a look at them. Thanks for mentioning them again. I will read them in hopes that they will help me to better understand what I’m doing here.

Thanks!

Thanks again for the suggestions for the JavaScript books. I’m working on Eloquent JavaScript.

In Chapter 2 of the book there are some exercises, and the author prefaces them with, “If you are unsure how to test your solutions to the exercises, refer to the Introduction.” This provides a link to the beginning of the introduction but I am not clear on which part of the intro addresses “how to test your solutions to the exercises.”

There is a paragraph under the heading “Code, and what to do with it,” that states,“I recommend you try your solutions to exercises in an actual JavaScript interpreter. That way, you’ll get immediate feedback on whether what you are doing is working, and, I hope, you’ll be tempted to experiment and go beyond the exercises.” So maybe this is the part of the intro that addresses “how to test your solutions to the exercises.”

The author mentions a JS interpreter but he does not provide any links or examples of JS interpreters. When I Google “what is a Javascript interpreter,” I get lots of results about JavaScript engines, which is not helpful, since I’m trying to figure out what a JavaScript interpreter is, not a JavaScript engine.

Am I correct in thinking that “how to test your solutions to the exercises” corresponds to “I recommend you try your solutions to exercises in an actual JavaScript interpreter”? If so, can you explain what a JavaScript interpreter is and where to find one?

thanks!

there is also this part:

When reading this book in your browser, you can edit (and run) all example programs by clicking them.

you can open an account on repl.it and there you have an editor that can give you a result to things as soon as you run the code

“engine” is just an informal term for interpreter. All modern web browsers have JavaScript interpreters, and node.js is an interpreter outside of a web browser.