JavaScript数组(ES6)

JavaScript数组一篇中介绍了ES6之前的数组方法。本篇介绍一下ES6里新增的数组方法。

  • find,findIndex,inclueds
  • fill,copyWithin
  • keys,values,entries
  • 静态方法(from,of)

find,findIndex,inclueds

find用于找元素,返回第一个满足条件的元素,找不到就返回undefined。函数声明:[].find( function(value, index, array) { … }, [thisArg] );。参照MDN

第一个参数是回调函数,它支持3个参数,第1个是遍历的数组内容,第2个是对应索引,第3个是数组自身。第二个参数thisArg可选,可用于以改变回调函数里面的this指针

var count = [1, 5, 10, 15].find(function(value, index, arr) {
    return value > 9;
});
console.log(count);     //10

findIndex用于找元素,返回第一个满足条件的元素的位置,找不到就返回-1。函数声明:[].findIndex( function(value, index, array) { … }, [thisArg] );,和上面find一样,不赘述。参照MDN

var idx = [1, 5, 10, 15].findIndex(function(value, index, arr) {
    return value > 9;
});
console.log(idx);   //2

这两个方法都可以发现NaN,弥补了之前indexOf方法的不足。indexOf方法无法识别数组的NaN元素,但findIndex方法可以借助Object.is方法做到:

var idx1 = [NaN].indexOf(NaN);
console.log(idx1);      //-1
var idx2 = [NaN].findIndex(y => Object.is(NaN, y));
console.log(idx2);      //0

includes用于找元素,找到返回true,找不到返回false。函数声明:[].includes(el, [start]);。参照MDN

第一个参数是查找的元素。第二个参数可选,表示开始查找的位置,不指定的话默认为0,指定为负数,表示倒着数。

[1, 2, 3].includes(2);      // true
[1, 2, 3].includes(4);      // false
[1, 2, 3].includes(3, 3);   // false
[1, 2, 3].includes(3, -1);  // true
[1, 2, NaN].includes(NaN);  // true

以前要看数组中是否包含某元素用indexOf:if (arr.indexOf(el) !== -1) { … }。除了感觉有点不自然外,也无法判断是否包含NaN。现在用includes就没这些问题了。

fill,copyWithin

fill用于填充当前数组,返回填充后的数组。函数声明:[].fill(value, [start, [end]]);。参照MDN

第一个参数是填充的元素,后两个参数可选,start是起始填充位置,不指定的话默认为0。end是填充到哪个位置之前结束,不指定的话默认到数组尾。位置可以指定负数,表示倒着数。

var arr = [1, 2, 3];
console.log(arr.fill(4));          // [4, 4, 4]
console.log(arr.fill(4, 1));        // [1, 4, 4]
console.log(arr.fill(4, 1, 2));     // [1, 4, 3]
console.log(arr.fill(4, -3, -2));   // [4, 2, 3]

用上面第一行例子,即单个参数,来初始化数组非常方便,数组中原有元素将全部被抹去。

copyWithin和fill很像,它用于将数组指定位置的元素复制到其他位置(会覆盖原来该位置的元素),最后返回修改后的数组。函数声明:[].copyWithin(target, [start, [end]]);。参照MDN

第一个参数和fill有区别,是从该位置开始替换元素。后两个参数参照fill,不赘述

var arr = ['a', 'b', 'c', 'd', 'e', 'f'];
console.log(arr.copyWithin(0, 3));   // ['d', 'e', 'f', 'd', 'e', 'f']

表示将从index为3开始直到数组结束的成员(即def)读取出来,替换从0号位开始的元素(即覆盖了abc)。

再看一个负数的例子:

var arr1 = [1, 2, 3, 4, 5];
console.log(arr1.copyWithin(-2, -3, -1));  // [1, 2, 3, 3, 4]

从倒数3位开始直到倒数1位(即34)读取出来,替换倒数2位(即覆盖了45)

keys,values,entries

这3个方法都用于遍历数组。都返回一个遍历器对象,可以用for…of循环进行遍历。区别是keys是对key的遍历,values是value的遍历,entries是对key-value的遍历。

函数声明都非常简单,一个参数都没有,分别是:[].keys();[].values();[].entries();。参照MDN

for (let index of ['a', 'b'].keys()) {
    console.log(index);
}
// 0
// 1

for (let elem of ['a', 'b'].values()) {
    console.log(elem);
}
// 'a'
// 'b'

for (let [index, elem] of ['a', 'b'].entries()) {
    console.log(index, elem);
}
// 0 "a"
// 1 "b"

因为返回的是遍历器对象,因此除了for…of循环外,也可以手动调用遍历器对象的next方法来遍历:

var arr = ['a', 'b', 'c'];
var eArr = arr.entries();
console.log(eArr.next().value);   // [0, 'a']
console.log(eArr.next().value);   // [1, 'b']
console.log(eArr.next().value);   // [2, 'c']

静态方法(from,of)

JavaScript数组一篇中介绍了ES6之前的数组方法,包括本篇上面所有Array的方法的函数声明都用了“[].方法名”的形式,等价于“Array.prototype.方法”,表示它们都是Array的实例方法。

但form和of的函数声明用了“Array.方法名”的形式,表示它们是Array的静态方法。(关于JS静态可以参照这里

from用于将类数组对象转为真正的数组。函数声明:Array.from(arrayLike, [mapFn, [thisArg]]);。参照MDN

第一个参数自然就是类数组对象。第二个参数作用类似于map,还可以为map指定this。有关类数组对象和map方法请参照JavaScript数组,不赘述。

现在用ES6的from方法来重写JavaScript数组一篇中的类数组对象中的例子:

处理arguments对象:

//ES5处理arguments对象:
var args = [].slice.call(arguments);

//ES6用from
var args = Array.from(arguments);

处理HTMLCollection对象:

//ES5用forEach遍历页面所有div,输入className
var divs = document.getElementsByTagName("div");
Array.prototype.forEach.call(divs, function(div) {  
    console.log("该div类名是:" + (div.className || "空"));
});

// ES6用from
Array.from(divs).forEach(function (div) {
    console.log("该div类名是:" + (div.className || "空"));
});

处理字面量对象:

//ES5
var arrayLike = { 0: "a", 1: "b", 2: "c", length: 3 };
var result = Array.prototype.map.call(arrayLike, function(s) {
    return s.toUpperCase();
});     
console.log(result);    //["A", "B", "C"]

//ES6
var result = Array.from(arrayLike, s => s.toUpperCase());   
console.log(result);    //["A", "B", "C"]

上面from用了第二个参数,该语句等价于Array.from(arrayLike).map(s => s.toUpperCase());

处理字符串:

//ES5
var result = Array.prototype.map.call("abc", function(s) {
    return s.toUpperCase();
});
console.log(result);    //["A", "B", "C"]

//ES6
var result = Array.from("abc", s => s.toUpperCase());     
console.log(result);    //["A", "B", "C"]

of作用和from类似,用于将一组值,转换为数组。函数声明:Array.of(el0, [el1, … , elN]);。参照MDN

和from一样, 同样是Array的静态方法,你无法用数组对象调用of方法。

console.log(Array.of(1,2,3));   // [1, 2, 3]

你可能会很疑惑,直接var arr = new Array(1,2,3);不就行了,要of方法有什么用?如果只有1个参数就有区别了:

//只有1个参数的普通构造函数
var arr1 = Array(3);
console.log(arr1);  // [, , ,]

//ES6用of就和上面有区别了
var arr2 = Array.of(3);
console.log(arr2);  // [3]

可以看出用of的话,可以完全替代构造函数,避免了单个参数导致的非常微妙的区别。它总是能返回一个数组,如果没有参数,就返回空数组[]

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 201,784评论 5 474
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 84,745评论 2 378
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 148,702评论 0 335
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,229评论 1 272
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,245评论 5 363
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,376评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,798评论 3 393
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,471评论 0 256
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,655评论 1 295
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,485评论 2 318
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,535评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,235评论 3 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,793评论 3 304
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,863评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,096评论 1 258
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,654评论 2 348
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,233评论 2 341

推荐阅读更多精彩内容