ES6 中的展开运算符你了解多少 ?

什么是展开运算符 (...)?

  • 展开运算符 :允许一个表达式在某处展开。展开运算符在多个参数(用于函数调用)或多个元素(用于数组字面量)或者多个变量(用于解构赋值)等地方可以使 用,作用就是 展开数组或字符串为一个新数组
  • 注意 : 展开运算符不能用在对象当中,因为目前展开运算符只能在可遍历对象(iterables)可用。iterables 的实现是依靠 [Symbol.iterator] 函数,而目前只有 Array,Set,String 内置 [Symbol.iterator] 方法,而 Object 尚未内置该方法,因此无法使用展开运算符。不过 ES7 草案当中已经加入了对象展开运算符特性。

怎么在函数调用中使用 ?

  • 在 ES6 之前,我们会使用 apply 方法将一个数组展开成多个参数 :
function test(a,b,c){/* code */}
var args = [0,1,2];
test.apply(null,args);
  • 上面代码,将 args 数组当作实参传递给了 a,b,c; 利用了 Function.prototype.apply 的特性。
  • 在 ES6 中,我们就可以更加简洁地来传递数组参数:使用 ...展开运算符就可以把 args 直接传递给 test() 函数。
function test(a,b,c){/* code */}
var args = [0,1,2];
test(...args);

怎么在数组字面量中使用 ?

  • 在 ES6 中,我们可以直接加一个数组直接合并到另外一个数组当中:
var arr1 = ['a','b','c'];
var arr2 = [...arr1,'d','e'];//['a','b','c','d','e']
  • 展开运算符也可以用在 push 函数中,可以不用再用 apply() / concat() 函数来合并两个数组:
var arr1 = ['a','b','c'];
var arr2 = ['d','e'];
arr1.push(...arr2);//['a','b','c','d','e']

怎么在解构赋值中使用 ?

  • 解构赋值也是 ES6 中的一个特性,而这个展开运算符可以用于部分情景:(解构赋值中展开运算符只能用在最后
let [arg1,arg2,...arg3] = [1,2,3,4];
console.log(arg1);//1
console.log(arg2);//2
console.log(arg3);//3,4
  • 注意 : 解构赋值中展开运算符只能用在最后:
let [arg1,...arg2,arg3] = [1, 2, 3, 4]; //报错

类数组对象变成数组 ?

  • 展开运算符可以将一个 类数组对象 变成一个真正的 数组对象
let list = document.querySelectorAll('div');
let arr = [...list];

总结一些常见的应用场景 ?


  • 复制数组 :
const fruits = ['apple','orange','banana'];
const fruitsCopied = [...fruits];//['apple','orange','banana']
console.log(fruits === fruitsCopied);//false
//ES5中的方法:old way
fruits.map(fruit => fruit);

注意 :…在展开基本数据类型时,是深copy,基本数据类型位于栈区;如果使用展开运算符 展开一个对象时,那么是浅copy,对象位于堆区;如果数组中是基本数据类型深copy;如果数组中有对象,就是浅copy;展开对象 对象就一层,是深copy;展开对象 对象是多层,是浅copy;可以通过  JSON.parse(JSON.stringify(obj)) 可以实现深copy 。

  • 数组去重 :
const fruits = ['apple', 'orange', 'banana', 'banana'];
const uniqueFruits = [...new Set(fruits)]; // ['apple', 'orange', 'banana']
// old way
fruits.filter((fruit, index, arr) => arr.indexOf(fruit) === index);
  • 合并数组 :
const fruits = ['apple', 'orange', 'banana'];
const vegetables = ['carrot'];
const fruitsAndVegetables = [...fruits, ...vegetables]; // ['apple', 'orange', 'banana', 'carrot']
const fruitsAndVegetables = ['carrot', ...fruits]; // ['carrot', 'apple', 'orange', 'banana']
// 老方法
const fruitsAndVegetables = fruits.concat(vegetables);
fruits.unshift('carrot');
  • 将参数作为数组进行传递 :

const mixer = (x, y, z) => console.log(x, y, z);
const fruits = ['apple', 'orange', 'banana'];
mixer(...fruits); // 'apple', 'orange', 'banana' 
// 老方法
mixer.apply(null, fruits);
  • 数组切片 :
const fruits = ['apple', 'orange', 'banana'];
const [apple, ...remainingFruits] = fruits; // ['orange', 'banana']
// 老方法
const remainingFruits = fruits.slice(1);
  • 将参数转换为数组 :

const mixer = (...args) => console.log(args);
mixer('apple'); // ['apple']
  • 将 NodeList (类数组)转换为数组 :
[...document.querySelectorAll('div')];
// 老方法
Array.prototype.slice.call(document.querySelectorAll('div'));
  • 复制对象 :
const todo = { name: 'Clean the dishes' };
const todoCopied = { ...todo }; // { name: 'Clean the dishes' }
console.log(todo === todoCopied); // false
// 老方法
Object.assign({}, todo);
  • 合并对象 :
const todo = { name: 'Clean the dishes' };
const state = { completed: false };
const nextTodo = { name: 'Ironing' };
const merged = { ...todo, ...state, ...nextTodo }; // { name: 'Ironing', completed: false }
// 老方法
Object.assign({}, todo, state, nextTodo);
  • 将字符串拆分为字符 :
const country = 'USA';
console.log([...country]); // ['U', 'S', 'A']
// 老方法
country.split('');
  • 求最大值 / 最小值 :
let numbers = [9, 4, 7, 1];
Math.max(...numbers); // 9
Math.min(...numbers); // 1

  • 0
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值