持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第16天,点击查看活动详情
Rest参数
- 在JavaScript中,无论函数是如何定义的,都可以使用任意数量的参数调用函数
- Rest参数可以通过使用...并在后面跟着包含剩余参数的数组名称,来将它们包含在函数定义中,代表将剩余参数收集到一个数组里
function sum(a,b){
return a+b
}
sum(1,2,3) //3
function sumAll(...args){
return args.reduce((previousValue, currentValue) => previousValue + currentValue,0);
}
sumAll(1,2,3,4,5) //15
- 同时也可以指定前面的参数为变量,剩余的参数收集起来
function fun(arg1,...rest){
console.log(arg1)
console.log(...rest)
}
fun() //undefined undefined
fun(1,2) // 1 2
fun(1,2,3) // 1 2 3
- 必须注意的是,rest参数必须放在参数列表的末尾,如果不在末尾,会报错
arguments变量
- 在没有rest参数的时候,使用arguments是获取函数所有参数的唯一方法
- 是一个类数组的对象,包含所有参数,可以迭代,但终究不是数组,不能使用数组方法
- 虽然包含所有参数,但不能像rest截取参数的一部分
function test(){
console.log(arguments.length)
console.log(arguments[0])
}
test()
//0
// undefined
test('a','b')
//2
//a
test('b','a')
//2
//b
- 箭头函数没有arguments,箭头函数中访问到的arguments不是箭头函数,而是属于调用箭头函数的普通函数
- 因此,箭头函数没有this也没有自己的arguments对象
Spread语法
- 一个和Rest参数相反的操作
- 在函数调用中使用...obj,会把可迭代对象obj展开到参数列表中
let arr = [1,2,3]
let maxNum = Math.max(...arr) // 3
let err = Math.max(arr) // error
- 可以用Spread语法合并数组
let arr1 = ['a','b','c']
let arr2 = ['m','n','t']
let newArr1 = [...arr1, ...arr2]//a,b,c,m,n,t
let newArr2 = [...arr2, ...arr1]//m,n,t,a,b,c
- 字符串可迭代,因此可以实现字符串转字符数组
let str = 'hello'
let arr = [...str] //h,e,l,l,o
- Spread语法使用了迭代器遍历对象,类似for-of
- 对象转为数组的操作,还可以使用Array.from,Array.from除了可以用于可迭代对象,还可用于类数组对象,因此Array.from的适用范围更大
- 浅拷贝对象和数组
let cat = ['c','a','t']
let newCat = [...cat]
JSON.stringify(cat) === JSON.stringify(newCat) // true
cat === newCat //false
newCat.push('t')
console.log(cat) // c,a,t
console.log(newCat) // c,a,t,t
总结
当出现...的时候,要么是Rest参数,要么是Spread语法
- 当出现在函数参数列表的最后,那么就是Rest参数,会把参数列表剩余的参数收集到一个数组中
- 当出现在函数调用/表达式中,那么就是Spread语法,会把一个数组展开为列表