Skip to content Skip to sidebar Skip to footer

Why Doesn't ["a","b","c"].map(string.prototype.tolowercase.call) Work?

This, of course, returns what you would expect: ['A','B','C'].map(function (x) { return x.toLowerCase(); }); // --> ['a', 'b', 'c'] So does using String.prototype.toLowerCa

Solution 1:

Similar Question: Why won't passing `''.trim()` straight to `[].map()`'s callback work?

Map has a optional thisArg which can be used like so:

['A', 'B', 'C'].map(Function.prototype.call, String.prototype.toLowerCase);  
// gives ["a", "b", "c"]

Solution 2:

This is a special behavior of JavaScript's dot-notation.

toLowerCase.call(x) is working because JavaScript uses toLowerCase as this while executing call. This is how call (which is the same Function.prototype.call you find on every function) knows you want it to execute toLowerCase.

Passing call into another function loses that reference, so this no longer refers to toLowerCase.

Solution 3:

The problem is that String.prototype.toLowerCase.call == Function.prototype.call. If you want to get a function that converts the argument to lower case, you could bind the toLowerCase function to the call function like that:

var toLowerCase = String.prototype.toLowerCase.call.bind(String.prototype.toLowerCase);
["A","B","C"].map(toLowerCase);

Solution 4:

But, this does not work:

["A","B","C"].map(String.prototype.toLowerCase.call);

The first argument passed to map is supposed to be a function that will be passed the value of members of the array. The above passes a direct reference to Function.prototype.call, so the function will attempt:

call(x);

So call has been passed without setting its this, so it will be undefined on entering the call function.

Post a Comment for "Why Doesn't ["a","b","c"].map(string.prototype.tolowercase.call) Work?"