var array1 = [1, 4, 9, 16];
map1=array1.map(Function.call,Number);
Why the output of map1 is [0,1,2,3], what this map function is doing?
Read up on the usage of Array#map here
Input args are map(callback, this)
In your example, you're supplying the function Function.call
as the mapper, which is the constructor for Function. Function is a basic way to say "run this function", and the this
you're binding is to give it the first arg.
Where it gets interesting, is the callback you give it takes args (currentValue, index)
. By passing through Function.call and binding it, you're actually forcing it to drop the first arg. This is a clever (read: difficult to understand) way of getting your "Number" function to run on the index.
e.g. try [1, 4, 9, 16].map(Function.call, String)
, and you'll see the same thing but parsed as strings ["1", "4", "9", "16"]
.
Let's step through what happens on the first iteration to get some more clarity:
Function.call
is invoked, passing args 1
(the current value), and 0
(the current index)Number
, before it executes, so it's like calling Function.call.bind(Number)(1, 0)
Function.call
says "bind to this context", but the explicit bind
call above overrides thisNumber(0)
, which is of course 0
, the index.Nowadays, I think most people would simply use an arrow function with a first arg they can ignore, e.g. array1.map((_, i) => Number(i))
(or better yet, Number.parseInt
, if you're trying to get an integer).
While this whole thing is very cool to read as a software developer, I wouldn't recommend this map(Function.call)
pattern in practice! If you've come across it in your own code, at least add a comment so the next dev doesn't need to come to SO :)