With the evolvement of JavaScript, lots of new features have been added this old but robust language. Among them are lots of functional programming language related functions like map, filter, each etc. In this post, we will cover one function map and its interesting behavior.
Before dive into the details, let first take an example, do you know the output of below function call?
['1', '7', '11'].map(parseInt)
You may think that it's easy and the output would be
[1, 7, 11]
Can you try to run this by yourself and you may be surprised of the output. The actual result is
[1, NaN, 3]
What's happening? Before getting into understanding why, let's understand some basic knowledge of JavaScript. When calling a function with parameters in JavaScript, if the number of parameters passed in is less than expected, the missing one will be undefined, in contrast, if the number of parameters passed in is more than expected, the extra ones will be ignored.
function foo(x, y) {
console.log(x);
console.log(y);
}
foo(1, 2); // 1, 2
foo(1); // 1, undefined
foo(1, 2, 3); // 1, 2
Also the parseInt() function has below signature.
parseInt(string, radix);
It takes two parameters, one is the value to be parsed and the other is the radix. For a normal number, the radix is 10, and also we can have radix like 2, 8, 16 etc. If the radix is empty or can be evaluated to false, the default radix 10 will be used. In addition, if a value is not within the radix system specified, the value will be evaluated to NaN.
So if we have number "1" and radix as 0, the parseInt() will return 1 as it is actually using radix 10 as original radix 0 is evaluated to false. And for value "7" and radix 1, since 7 is not within the radix 1 scope, hence 7 would be evaluated to NaN.
We are missing the last piece, the map() function. According to definition, map() has below signature.
var new_array = arr.map(function callback(currentValue[, index[, array]]) {
// Return element for new_array
}[, thisArg])
For each element in the arr, the callback function will be invoked with three parameters: the actual element value, the index of the element in the array, the array itself.
Now combing all knowledge above, let's see this statement again.
['1', '7', '11'].map(parseInt)
So what it does is actually:
parseInt("1", 0, ['1', '7', '11']);
parseInt("7", 1, ['1', '7', '11']);
parseInt("11", 2, ['1', '7', '11']);
The output will be 1, NaN, 3 respectively. Hope this clears some doubts you have on map.