ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

JS 手写之 Function.prototype.call

2021-05-29 22:03:33  阅读:149  来源: 互联网

标签:Function uniqueKey 对象 args ctx call prototype 方法


Function.prototype.call

call() 方法使用一个指定的 this 值和单独给出的一个或多个参数来调用一个函数。

注意: 该方法的语法和作用与 apply() 方法类似,只有一个区别,就是 call() 方法接受的是一个参数列表,而 apply() 方法接受的是一个包含多个参数的数组。

语法

function.call(thisArg, arg1, arg2, ...)

参数

  • thisArg - 可选的。在 function 函数运行时使用的 this 值。请注意,this 可能不是该方法看到的实际值:如果这个函数处于非严格模式下,则指定为 null 或 undefined 时会自动替换为指向全局对象,原始值会被包装。
  • arg1, arg2, ... - 指定的参数列表。

返回值

使用调用者提供的 this 值和参数调用该函数的返回值。若该方法没有返回值,则返回 undefined。

描述

call() 允许为不同的对象分配和调用属于一个对象的函数/方法。

call() 提供新的 this 值给当前调用的函数/方法。你可以使用 call 来实现继承:写一个方法,然后让另外一个新的对象来继承它(而不是在新对象中再写一次这个方法)。

Function.prototype.myCall

// 和apply的唯一区别就是入参被拆开了
Function.prototype.myCall = function (ctx, ...args) {
  // 避免上下文不传,缺省值为 window 全局对象
  ctx ||= window;
  // 创建一个唯一的 Symbol 避免对象属性重复
  const uniqueKey = Symbol("fn");
  // 保存当前的 this,当前的 this 原来指向调用它的方法
  ctx[uniqueKey] = this;

  // 对象调用保存的方法, 此时 this(原方法) 指向被修改为ctx
  const res = args.length > 0 ? ctx[uniqueKey](...args) : ctx[uniqueKey]();
  // 删除对象的属性,减少内存占用
  delete ctx[uniqueKey];
  return res;
};

测试

var target = "world";
var context = {
  target: "universe",
};
function fn() {
  const args = Array.from(arguments).join(" ");
  console.log(`${args} ${this.target}!!!`);
}

fn.call(context, "hello", "all", "the"); // hello all the universe!!!
// 可以发现,this 的指向已经被修改到 context
fn.myCall(context, "hello", "all", "the"); // hello all the universe!!!

标签:Function,uniqueKey,对象,args,ctx,call,prototype,方法
来源: https://www.cnblogs.com/frank-link/p/14826513.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有