思路
map 迭代方法接收两个参数:
- 对每一项执行的函数
- 该函数接收三个参数:
- 数组项的值
- 数组项的下标
- 数组对象本身
- 该函数接收三个参数:
- 指定 this 的作用域对象
map 方法返回每次函数调用结果组成的数组。
代码表示:
arr.map(function(item, index, arr) {}, this);
实现
由此,实现 fakeMap 方法如下
方法一:
Array.prototype.fakeMap = function fakeMap(fn, context) { if (typeof fn !== "function") {//判断fn是否能为函数,如果不是,跑出错误 throw new TypeError(`${fn} is not a function`); } let arr = this; let temp = []; for (let i = 0; i < arr.length; i++) { // 迭代执行 let result = fn.call(context, arr[i], i, arr); temp.push(result); } return temp; };
检测:
let arr = ["x", "y", "z"];
arr.fakeMap((item, index, arr) => console.log(item, index, arr));
输出:
x 0 [ ‘x’, ‘y’, ‘z’ ] y 1 [ ‘x’, ‘y’, ‘z’ ] z 2 [ ‘x’, ‘y’, ‘z’ ]
this 指向:
let arr = ["x", "y", "z"]; let obj = { a: 1 }; arr.fakeMap(function() { console.log(this.a); }, obj);
输出
1 1 1
更新
Array.prototype.myMap = function (fn, context) { const array = this context = Object(context) || global // 严格模式下 const resultArr = [] for (let i = 0; i < array.length; i++) { let item = array[i] result = fn.call(context, item, i, array) resultArr.push(result) } return resultArr };
注: 严格模式下,context 为 null 或 undefined 时 Object(context) 返回空对象,不会被赋值为global
方法二:
Array.prototype.myMap = function () { var arr = this var [fn, thisValue] = Array.prototype.slice.call(arguments) var result = [] for (var i = 0; i < arr.length; i++) { result.push(fn.call(thisValue, arr[i], i, arr)) } return result } var arr0 = [1, 2, 3] console.log(arr0.myMap(v => v + 1))