Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
250 views
in Technique[技术] by (71.8m points)

javascript - String methods with higher-order functions

I ran into a weird thing while trying to use String methods with higher-order functions. This will throw an error:

['a', 'b'].some('boo'.includes)

I have to wrap the predicate in another function to make it work. But isn't 'boo'.includes already a function?

This works with plain functions:

const boo = {
    includes: () => true
};

['a', 'b'].some(boo.includes)

Is there some special property of String methods that prevents them from being composed like this?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

"boo".includes is nothing else than String.prototype.includes. Calling it on the string "boo" however sets this to "boo", which gives the proper context to the function. E.g. "boo".includes("b") is the same as String.prototype.includes.call("boo", "b").

Passing it as an argument, e.g. ['a', 'b'].some('boo'.includes), is the same as ['a', 'b'].some(String.prototype.includes), which then lacks the proper this as context.

You can of course use e.g. bind: ['a', 'b'].some(String.prototype.includes.bind("boo")), or use the optional second parameter thisArg for some: ['a', 'b'].some(String.prototype.includes, "boo"). This will get rid of the error. However, you will then notice, that some passes not only the element, but the index as second parameter, and the array itself as third. This is a problem, as includes also takes an optional second parameter for the start position. This causes likely unwanted behavior, as e.g. the array element "b" is at index 1, and "boo".includes("b", 1) === false.

All in all, you need a function which is so different to String.prototype.includes, that it's just easier to wrap it in a new function that actually does what you want: ['a', 'b'].some(e => "boo".includes(e)), as you already noticed.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...