001 Array 类型

《JavaScript 高级程序设计》这本书被称为 JavaScript 编程的圣经,又称为红宝书。记得这本书是我在刚学前端那会和犀牛书一起购买的,这期间断断续续翻了翻,大部分都处于落灰状态。
这本书很经典,关于 JavaScript 编程的方方面面基本上都讲到了,要是能够通读一遍,可以省去一些翻文档和查资料的时间,这本书的内容也是挺丰盛的,因此我专门建了一个文集,用来做一些读书笔记,以在忘记某块知识时能够回头翻一翻。

判断数组

关于判断数组,这里总结两种方式:
1.使用 Object 原型链上的 toString 方法判断:

function isArray(arr){
    return Object.prototype.toString.call(arr).indexOf("Array") !== -1
}

isArray([]) // true
isArray({}) // false

2.使用 Array 对象上原生的 isArray 方法:

Array.isArray([]) //true
Array.isArray({}) //false

数组的 toString 方法

调用数组的 toString 方法,会依次调用数组每一项的 toString 方法,然后将返回值使用逗号进行拼接:

const arr = [{a:1},[],1,2,"hello"]
arr.toString() // "[object Object],,1,2,hello"

同理,调用数组的 toLocaleStringvalueOf 方法时也会依次调用数组各项元素的 toLocaleStringvalueOf 方法,然后使用逗号进行拼接。
我们也可以修改数组各项元素的 toString 方法,以取代默认结果:

let ele1 = {
    name:"ele1",
    toString(){
        return "么么哒"
    }
}
let ele2 = {
    name:"ele2",
    toString(){
        return "呵呵哒"
    }
}
const arr = [ele1,ele2]

arr.toString() //"么么哒,呵呵哒"

对于数组的 toLocaleStringvalueOf 方法同样适用。

栈/队列方法

我们可以使用数组来模拟栈或者队列数据结构。
栈方法:pushpop

let arr = []
arr.push(1,2)
arr.pop() //2
arr.pop() //1

对列方法:pushshift

let arr = []
arr.push(1,2)
arr.shift() //1
arr.shift() //2

反向队列:unshiftpop

let arr = []
arr.unshift(1,2)
arr.pop() //2
arr.pop() //1

排序方法

1.reverse 方法:
该方法用来对数组进行反转:

let arr = [1,2,3]
arr.reverse() // [3,2,1]

2.sort 方法
该方法用来对数组进行排序,默认按照升序排序,并且在排序时通过元素的 toString 进行位置比较。
因此下面的排序可能不是我们想要的结果:

let arr = [1,2,10,3,20]
arr.sort() //[1,10,2,20,3]

除此之外,sort 方法可以接受一个函数作为参数,用来自定义排序规则。
该参数函数接受两个待比较的元素作为参数,函数返回值决定了这两个元素的排序:

  • 返回值小于 0,升序
  • 返回值大于 0,降序
  • 返回值等于 0,表示这两个参数相等,按照参数顺序排序
let arr = [1,2,10,20,3]
arr.sort((prev,next) => prev - next) // [1, 2, 3, 10, 20]

以上的方法适用于元素的 valueOf 方法返回数值(或者可以隐式转换为数值)的情况,因为只有数值才可以做减法的。如果元素的 valueOf 方法返回的不是数值(或者可以隐式转换为数值),就需要我们手动进行判断,然后进行返回:

let arr = [{val:1},{val:2},{val:10},{val:20},{val:3}]
arr.sort((prev,next) => {
    return prev.val - next.val
}) //  [{val:1},{val:2},{val:3},{val:10},{val:20}]

注意:reversesort 方法都会在原始的数组上进行修改。

操作方法

1.concat 方法
该方法用来进行数组合并,接受的参数如下:

  • 无参数:返回一个当前数组的副本
  • 参数为一个或多个变量、数组:合并当前数组和参数元素,返回合并后的数组

如果参数中含有数组,则会将该数组拆开,并合并到新数组中。

[].concat(1,2,[3,[4,5]]) //[1,2,3,[4,5]]

该方法不会对原始数组进行修改。
2.slice 方法
该方法用来从原始数组中截取一部分元素,基于这些元素再创建一个新数组。
slice 方法的参数:

  • 起始位置:截取数组时的起始位置,可为负数,可选,默认为0
  • 结束位置:截取数组时的结束位置,可为负数,可选,默认为数组的长度

slice 的参数为负数时,该参数和数组长度的和就是实际截取时的启示/结束位置,如果结束位置(经计算转化后)小于起始位置(经计算转化后),则返回一个空数组。

[1,2,3].slice() //[1,2,3]
[1,2,3].slice(1) //[2,3]
[1,2,3].slice(-2,-1) //[2]
[1,2,3].slice(-1,-2) //[]
...

slice 方法不会修改原始数组。
3.splice 方法
该方法较强大,可以用来删除、插入、替换数组元素。该方法会对原始数组进行修改。
1)删除元素
使用 splice 方法删除数组元素需要两个参数:

  • 删除元素的起始位置
  • 删除元素的个数

返回被删除的元素组成的数组。

let arr = [1,2,3]
arr.splice(0,1) //[1]
arr //[2,3]

2)插入元素
使用 splice 方法插入元素需要至少三个参数:

  • 插入的起始位置
  • 0 (表示不删除元素)
  • 插入的元素序列,可为多个

由于没有删除元素,因此调用该方法返回一个空数组

let arr = [1,2,3]
arr.splice(0,0,"memeda","heheda") //[]
arr // ["memeda", "heheda", 1, 2, 3]

3)替换元素
使用 splice 方法替换元素的原理是先删除该元素,在在其位置上进行替换,在替换时可以使用多个元素序列。

let arr = [1,2,3]
arr.splice(1,1,"memeda","heheda") //[2]
arr //[1, "memeda", "heheda", 3]

位置方法

数组中有两个位置方法:indexOflastIndexOf,这两个方法用来查找元素在数组中的位置。indexOf 是从数组开头开始寻找,找到第一个匹配的元素便停止,如果没有匹配到元素,则返回 -1,lastIndexOf 从数组的结尾开始寻找,匹配方式类似。
需要注意的是,indexOflastIndexOf 匹配元素时要求严格相等(===)。
另外,这两个方法还可以接受起始位置和结束位置两个参数(可选),表示搜寻的位置。

let person = {name:"MIKE"}
let arr1 = [{name:"MIKE"}]
let arr2 = [person]
arr1.indexOf(person) //-1
arr2.indexOf(person) //0

由于使用 indexOflastIndexOf 方法匹配元素时要求严格相等,因此 arr1 数组并不能匹配到 person 对象。

迭代方法

数组还有几个迭代方法,用来对数组内部的元素做一些迭代操作,这些方法都接受一个函数作为参数,每次进行迭代时都会执行该函数。该函数的参数为:值、位置、原数组
1.every 方法
该方法用来对数组的每一项进行迭代,如果函数对每一个元素都返回 true,则 every 的返回结果为 true

[1,2,3].every((v)=> v>0) //true
[1,2,3].every((v)=> v>1) //false

2.some 方法
该方法和 every 方法类似,但不要求函数对每一个元素返回 true,只要有一个元素在迭代时返回 truesome 方法就返回 true
true,则 every 的返回结果为 true

[1,2,3].some((v)=> v>0) //true
[1,2,3].some((v)=> v>1) //true

3.filter 方法
该方法用来对数组的每一项进行过滤,返回符合要求的元素列表.

[1,2,3].filter(v=>v%2) //[1,2]

4.forEach 方法
该方法用来对数组的每一项进行操作,该方法没有返回值,也不会影响原始数组,类似于普通的 for 循环。

[1,2,3].forEach(v=>{ console.log(v) }) // 1,2,3

5.map 方法
该方法用来对数组的每一项进行操作,然后将操作的结果映射到一个新数组。

[1,2,3].map(v=>v*2) //[2,4,6]

归并方法

数组还有两个归并方法:reducereduceRight
这两个方法会对数组的每一项进行迭代,然后构建一个最终的返回值。可以接受四个参数:

  • 前一个值
  • 后一个值
  • 当前索引
  • 原数组对象

在迭代的过程中,函数的返回值会作为第一个参数传入下一次的迭代的函数中,并最终返回一个最终值。在第一次进行迭代时,前一个参数和后一个参数分别是数组的第一个元素和第二个元素。
reduceRight 从数组的末尾开始归并,其他和 reduce 一致。

// 对数组的每一项相乘
[1,2,3,4,5].reduce((prev,next) => prev * next) //120
[1,2,3,4,5].reduceRight((prev,next) => prev + next) //15

当涉及到对数组元素的累加、累积等操作时,这两个方法很好用。

完。

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

推荐阅读更多精彩内容

  • 第5章 引用类型(返回首页) 本章内容 使用对象 创建并操作数组 理解基本的JavaScript类型 使用基本类型...
    大学一百阅读 3,211评论 0 4
  • 前言 把《C++ Primer》[https://book.douban.com/subject/25708312...
    尤汐Yogy阅读 9,504评论 1 51
  • 我以为我已经不再渴望收到礼物 可是当它出现在我眼前 我的心瞬间充盈 仿佛回到初恋 心仪的礼物 一定是懂你的人才会送...
    摄影师静心阅读 375评论 1 1