Function.prototype.call()
Calls a function with an explicit this value and arguments supplied individually.
call(thisArg)
call(thisArg, arg1)
call(thisArg, arg1, arg2)
call(thisArg, arg1, arg2, /* …, */ argN)- Added in JavaScript ECMAScript 3 (1999)
Parameters
| Parameter | Type | Description |
|---|---|---|
$thisArg | any | The value to use as this when calling the function. If the function is not in strict mode, null and undefined are replaced with the global object, and primitive values are converted to objects. |
$arg1, …, argNoptional | any | Arguments for the function, listed one at a time. |
Return value
anyThe result of calling the function with the specified this value and arguments.
Errors
Throws a TypeError if the value it is called on is not callable, and also when used on a class constructor, since classes cannot be called without new.
Changelog
- PHP ECMAScript 5 (2009)Strict-mode functions no longer substitute the global object for a null or undefined thisArg, and no longer box primitive thisArg values into wrapper objects.
- PHP ECMAScript 2015Arrow functions ignore thisArg entirely — their this is fixed lexically at creation time.
call() runs a function right now, with a this value you choose, passing arguments one at a time. It is the twin of apply(), which takes the same arguments packed into an array.
When to reach for it
- Method borrowing. Run a prototype method against an object that does not inherit it — the classic
Array.prototype.slice.call(arrayLike)orObject.prototype.toString.call(value)type tag. - Calling an unbound helper against a specific receiver in a single expression, where
bind()would allocate a function you throw away immediately. - Escaping shadowed methods. If an object defines its own
hasOwnProperty,Object.prototype.hasOwnProperty.call(obj, key)still works.
What trips people up
The thisArg is not passed through untouched in sloppy mode. A non-strict function receiving null sees globalThis, and receiving 7 sees a Number wrapper object — so typeof this reports "object", not "number". Strict-mode functions, class bodies and modules skip that substitution and get the raw value.
Arrow functions have no own this, so call() cannot retarget one; the thisArg is silently ignored rather than producing an error. And call() cannot chain constructors — use Reflect.construct() or extends.
Example
When to use it
- Apply Array.prototype.slice or join to an array-like object such as arguments
- Get a reliable type tag with Object.prototype.toString.call(value)
- Call Object.prototype.hasOwnProperty on an object whose own property shadows it
- Invoke a shared helper against one specific object without creating a bound copy
Frequently asked questions
What is the difference between call() and apply()?
They are identical except for how arguments are delivered: call() takes them listed individually, apply() takes them as a single array or array-like. Both invoke the function immediately with the this value you supply. In modern code, spread syntax (fn(...args)) usually replaces apply().
Why is this still not what I passed to call()?
Because the target function is non-strict and JavaScript substituted the value. Non-strict functions replace null and undefined with globalThis and wrap primitives in object wrappers. Add "use strict", use a class method, or run as a module and the exact value you passed comes through.
Can I use call() on an arrow function?
You can call it, but the thisArg is ignored. Arrow functions capture this from the scope where they were written and no call, apply or bind can change it. Use a regular function expression if you need the caller to choose this.
More examples
Running one helper against different receivers
bump is never a property of anything. The first call gives it a Counter instance as this and returns 15; the second gives it a plain object and returns 3. The last line shows that when a function ignores this, any placeholder such as null works.
class Counter {
constructor(start) {
this.count = start;
}
}
function bump(by) {
this.count += by;
return this.count;
}
console.log(bump.call(new Counter(10), 5));
console.log(bump.call({ count: 0 }, 3));
// Built-ins that ignore this still need a placeholder
console.log(Math.max.call(null, 4, 9, 1));How thisArg is coerced in strict and non-strict code
The non-strict function turns null into globalThis and boxes 7 into a Number object, so typeof this is "object" both times. The strict function receives null and 7 exactly as passed. This is the single most common surprise with call().
// Function() bodies are non-strict, whatever surrounds them
const sloppy = new Function("return [typeof this, this === globalThis];");
console.log("non-strict null ->", sloppy.call(null));
console.log("non-strict 7 ->", sloppy.call(7));
function strict() {
"use strict";
return [typeof this, this];
}
console.log("strict null ->", strict.call(null));
console.log("strict 7 ->", strict.call(7));
Discussion