push办法
Array.prototype.push = function (...items) { let O = Object(this); // ecma 中提到的先转换为对象 // >>> 无符号右移 let len = this.length >>> 0 let argCount = items.length >>> 0 // 2 ^ 53 - 1 为JS能示意的最大正整数 if (len + argCount > 2 ** 53 - 1) { throw new TypeError("The number of array is over the max value") } for (let i = 0; i < argCount; i++) { O[len + i] = items[i]; } let newLength = len + argCount; O.length = newLength; return newLength;}
pop 办法
Array.prototype.pop = function() { let O = Object(this); let len = this.length >>> 0; if (len === 0) { O.length = 0; return undefined; } len --; let value = O[len]; delete O[len]; O.length = len; return value;}
map办法
Array.prototype.map = function(callbackFn, thisArg) { if (this === null || this === undefined) { throw new TypeError("Cannot read property 'map' of null"); } if (Object.prototype.toString.call(callbackfn) != "[object Function]") { throw new TypeError(callbackfn + ' is not a function') } let O = Object(this); let T = thisArg; let len = O.length >>> 0; let A = new Array(len); // 赋值给新数组,并不扭转原数组的值 for(let k = 0; k < len; k++) { if (k in O) { let kValue = O[k]; // 顺次传入this, 以后项,以后索引,整个数组 let mappedValue = callbackfn.call(T, KValue, k, O); A[k] = mappedValue; } } return A;}
reduce办法
两个留神点
- 初始值默认值不传的非凡解决;
累加器以及 callbackfn 的解决逻辑。
Array.prototype.reduce = function(callbackfn, initialValue) {// 异样解决,和 map 相似if (this === null || this === undefined) { throw new TypeError("Cannot read property 'reduce' of null");}// 解决回调类型异样if (Object.prototype.toString.call(callbackfn) != "[object Function]") { throw new TypeError(callbackfn + ' is not a function')}let O = Object(this);let len = O.length >>> 0;let k = 0;let accumulator = initialValue; // reduce办法第二个参数作为累加器的初始值if (accumulator === undefined) { throw new Error('Each element of the array is empty'); // 初始值不传的解决 for(; k < len ; k++) { if (k in O) { accumulator = O[k]; k++; break; } }}for(;k < len; k++) { if (k in O) { // 留神 reduce 的外围累加器 accumulator = callbackfn.call(undefined, accumulator, O[k], O); }}return accumulator;}