引入
续借上文,这篇文章主要讲的是数组原型链相关的考题,有些人可能会纳闷,数组和原型链之间有什么关系呢?我们日常使用的数组forEach
,map
等都是建立在原型链之上的。举个🌰,如我有一个数组const arr = [1,2,3]
我想要调用arr.sum
方法对arr
数组的值进行求和,该如何做呢?我们知道数组没有sum
函数,于是我们需要在数组的原型上定义这个函数,才能方便我们调用,具体代码如下。接下来我们就是采用这种方式去实现一些数组常用的方法。
Array.prototype.sum = function () { let sum = 0; for (let i = 0; i < this.length; i++) { sum += this[i]; } return sum; }; const arr = [1,2,3]; console.log(arr.sum()); // 6
正文
forEach实现
首先,我们先了解forEach
这个函数有哪些参数。我们先看一个例子, forEach
的使用
const arr = [1,2,3]; arr.forEach((item,index,arr) => { console.log(item,index,arr); }) /** 输入如下 1 0 [ 1, 2, 3 ] 2 1 [ 1, 2, 3 ] 3 2 [ 1, 2, 3 ] **/
所以我们观察发现forEach
传的是一个回调函数
function(currentValue, index, array) {}
这个回调函数有三个参数,分别如下
currentValue
:必需,当前正在遍历的数组元素的值。index
:可选,当前正在遍历的数组元素的索引。array
:可选,指向正在被遍历的数组对象本身。
了解上述资料后,于是我们可以自己实现一个myForEach
,代码如下
Array.prototype.myForEach = function (fn) { for (let i = 0; i < this.length; i++) { fn(this[i], i, this); } }; const arr = [1, 2, 3]; arr.forEach((item, index, arr) => { console.log(item, index, arr); }); /** 1 0 [ 1, 2, 3 ] 2 1 [ 1, 2, 3 ] 3 2 [ 1, 2, 3 ] **/
map实现
同样,我们了解下map
的方法有哪些参数,调研发现map
的参数与forEach
的参数前面一致,多了一个thisArg
的参数
thisArg
: 在执行回调函数时作为其上下文(即this
值)的对象。如果提供了这个参数,回调函数内部的this
将指向它;如果不提供,则在严格模式下this
会是undefined
,在非严格模式下this
通常是全局对象(如浏览器环境中的window
对象
我们也看一个🌰,帮助大家会一起map
是如何使用的
const arr = [1, 2, 3]; // 这里为了能让大家看到所有的参数,于是将三个参数全部写了下来 const douleArr = arr.map((value,index,array) => value * 2); console.log(douleArr); /** 输入如下 [2, 4, 6] **/
那么该如何实现呢,其实依靠forEach
照葫芦画瓢即可,代码如下
Array.prototype.myMap = function (fn, thisArg) { const res = []; for (let i = 0; i < this.length; i++) { const mappedValue = fn.call(thisArg, this[i], i, this); res.push(mappedValue); } return res; }; const arr = [1, 2, 3]; const douleArr = arr.myMap((value,index,array) => value * 2); console.log(douleArr); /** 输入如下 [2, 4, 6] **/
最后,这就是本章节的内容,之后有机会再更几个手写数组原型链的函数