ES7中的includes
ES7中的includes
在ES7中,数组方法includes被提出,这个方法被提出的考虑是,在开发过程中,indexOf方法其实处于一个很尴尬的地位,indexOf接受一个参数,返回当前的被查询元素在数组中的位置,不存在时返回-1。我们的工程师使用这个方法的时候不能直接使返回值转布尔值这样判断,经常写一些额外的检查语句,比如arr.indexOf(1) > -1
。
var arr = [1, 2, 3, 4, 5, 6, 7, 8, 9];
if (arr.indexOf(1)) {
console.log('存在');
}
if(arr.indexOf(1) > -1){
console.log('存在'); // 存在
}
甚至在数组中存在NaN的时候,这个方法也会失效
var arr = [1, 2, 3, 4, 5, NaN, 7, 8, 9];
console.log(arr.indexOf(NaN)); // -1, 这里我们预期的输出是5
所以ES7提出了这个includes函数,这个函数可以接收两个参数,第一个参数是想查询的参数。第二个参数是数字类型,代表索引,如果这个参数大于等于数组的长度,则会返回 false,且该数组不会被搜索。如果这个参数为小于零,则需要对这个参数进行计算(数组长度 + 索引参数),如果计算出的结果小于零,则整个数组都会被搜索。
由于是ES7,所以部分项目是需要对其进行babel转ES5代码的,事实上很多的JavaScript库都已经做到了这一点,但是我们希望能自己写一次,也让自己对于这块的理念思想有些自己的体验。
我做的兼容代码如下,注释也尽量详细了,希望对大家有所帮助,谢谢
// 判断你的环境是否支持includes方法。若想测试你的代码,可删除此外层判断
if (!Array.prototype.includes) {
/**
* 给数组原型链绑定原型方法includes
**/
Object.defineProperty(Array.prototype, 'includes', {
value: function (findAttr, fromIndex) {
// this为null时报错。undefined不用考虑,当this为undefined时,在调用之前就应该报错了。
if (this === null) {
throw new TypeError('"this" is null or not defined');
}
// 一定是数组,不然不会进入这个方法,所以可以不用类型判断
var parArr = Object(this);
// 数组长度
var len = parArr.length;
// 若数组为空,直接返回false
if (!len) {
return false;
}
// 索引
var n = fromIndex || 0;
// 当n为小数的时候,n为数组长度加上n,若计算出的数字小于0,会遍历整个数组,所以最小由0表示即可
n = Math.max(n >= 0 ? n : len + n, 0);
// 若数组为空,直接返回false
if (n >= len) {
return false;
}
// 对比函数
function compare(x, y) {
// NaN的原型是Number,但是 NaN === NaN => false
return x === y || (typeof x === 'number' && typeof y === 'number' && isNaN(x) && isNaN(y));
}
// n代表需要查找的数组起点位置,左闭右开
while (n < len) {
// 判断是否相等
if (compare(findAttr, parArr[n++])) {
return true;
}
}
return false;
},
})
}