Call Polyfill

Function.prototype.callPolyfill = function (context = {}, ...args) {
  if (typeof this !== "function") {
    throw new Error("Attach call to a function");
  }
  context.fn = this;
  context.fn(...args);
};

const User = {
  name: "Arjunan",
};

function myFunction(age, weight) {
  console.log(this.name);
  console.log(age, weight);
}

myFunction.callPolyfill(User, 12, 100);
// Arjunan
// 12 100

Apply Polyfill

Function.prototype.applyPolyfill = function (context = {}, args = []) {
  if (typeof this !== "function") {
    throw new Error("Attach apply to a function");
  }
  if (!Array.isArray(args)) {
    throw new Error("Add arguments inside a array");
  }
  context.fn = this;
  context.fn(...args);
};

const User = {
  name: "Arjunan",
};

function myFunction(age, weight) {
  console.log(this.name);
  console.log(age, weight);
}

myFunction.applyPolyfill(User, [12, 100]);
// Arjunan
// 12 100

Bind Polyfill 1

Function.prototype.bindPolyfill = function (context, ...args) {
  let fn = this;
  return () => {
    fn.apply(context, args);
  };
};

const User = {
  name: "Arjunan",
};

function myFunction(age, weight) {
  console.log(this.name);
  console.log(age, weight);
}

const bindedMyFunction = myFunction.bindPolyfill(User, 12, 100);
bindedMyFunction();
// Arjunan
// 12 100

Bind Polyfill 2

Function.prototype.bindPolyfill = function (context = {}, ...args) {
  if (typeof this !== "function") {
    throw new Error("Attach apply to a function");
  }

  context.fn = this;
  return (...newArgs) => {
    context.fn(...args, ...newArgs);
  };
};

const User = {
  name: "Arjunan",
};

function myFunction(age, weight) {
  console.log(this.name);
  console.log(age, weight);
}

const bindedMyFunction = myFunction.bindPolyfill(User, 12);
bindedMyFunction(100);
// Arjunan
// 12 100