Implementing a Custom call() Method in JavaScript
The call() method in JavaScript allows you to invoke a function with a specific this value and individual arguments. It is one of the fundamental methods for controlling the execution context of functions in JavaScript.
Let’s implement a custom version of the call() method.
What is call()?
The call() method is used to invoke a function, explicitly specifying the this value and passing in arguments one by one. This is especially useful in cases where you want to call a method of one object on another object.
Real Interview Insights
Interviewers might ask you to:
- Implement a function that mimics the behavior of JavaScript’s built-in 
call()method. - Ensure that the function handles different types of arguments correctly.
 - Make sure the function properly changes the 
thiscontext. 
Implementing customCall Function
Here’s how you can implement a custom call() function:
Function.prototype.customCall = function(context, ...args) {
  // If context is null or undefined, default it to the global object (window in browsers)
  context = context || globalThis;
 
  // Create a unique property on the context to avoid overwriting existing properties
  const fnSymbol = Symbol();
  context[fnSymbol] = this;
 
  // Call the function with the provided arguments
  const result = context[fnSymbol](...args);
 
  // Remove the temporary property from the context
  delete context[fnSymbol];
 
  return result;
};Explanation:
- Setting the Context: We first ensure that if the 
contextisnullorundefined, it defaults to the global object (globalThis). This mimics the behavior of JavaScript’scall()method. - Temporary Property: We assign the function (using 
this) to a unique property on thecontextobject. This is done usingSymbol()to avoid name collisions. - Function Invocation: We then invoke the function with the provided arguments using the 
...argsspread operator. - Clean-Up: After the function call, we remove the temporary property from the 
contextobject to avoid side effects. 
Practical Examples
Let's see the customCall function in action:
function greet(greeting, punctuation) {
  return `${greeting}, ${this.name}${punctuation}`;
}
 
const person = { name: 'Alice' };
 
// Using the custom call method
console.log(greet.customCall(person, 'Hello', '!')); // Output: "Hello, Alice!"
 
// Another example with different context
const person2 = { name: 'Bob' };
console.log(greet.customCall(person2, 'Hi', '.')); // Output: "Hi, Bob."Handling Edge Cases
- Primitive 
thisValues: Whenthisis set to a primitive value (like a number or string), it should be automatically converted to an object (e.g.,NumberorStringobject). - Functions without Arguments: Ensure that the implementation works correctly even when no arguments are passed.
 - Null and Undefined Contexts: If the context is 
nullorundefined, it should default to the global object. 
Use Cases for call()
- Reusing Functions: Invoke a function with a different 
thisvalue, allowing one function to be used by multiple objects. - Inheritance: Call a parent object's method on a child object.
 - Event Handlers: Set the context in event handlers or callbacks.