ECMAScript 2015新增了Set
类。我们可以基于ES6的Set
开发我们的Set
类。
关于ECMAScript 6的
Set
类的实现细节,请查阅https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global-Objects/Set(或http://goo.gl/2li2a5)。
我们先看看原生的Set
类怎么用。
还是用我们原来测试Set
类的例子:
let set = new Set;set.add(1);console.log(set.values); // 输出@Iteratorconsole.log(set.has(1)); // 输出trueconsole.log(set.size); // 输出1
和我们的Set
不同,ES6的Set
的values
方法返回Iterator
(第2章提到过),而不是值构成的数组。另一个区别是,我们实现的size
方法返回set
中存储的值的个数,而ES6的Set
则有一个size
属性。
可以用delete
方法删除set
中的元素:
set.delete(1);
clear
方法会重置set
数据结构,这跟我们实现的功能一样。
ES6 Set
类的操作
我们的Set
类实现了并集、交集、差集、子集等数学操作,然而ES6原生的Set
并没有这些功能。不过,有需要的话,我们也可以模拟。
我们的例子会用到下面两个集合:
let setA = new Set;setA.add(1);setA.add(2);setA.add(3);let setB = new Set;setB.add(2);setB.add(3);setB.add(4);
模拟并集操作
我们可以创建一个新的集合,用来添加两个集合中所有的元素(行
{1}
)。迭代这两个集合(行{2}
、行{3}
),把所有元素都添加到并集的集合中。代码如下:let unionAb = new Set; //{1}for (let x of setA) unionAb.add(x); //{2}for (let x of setB) unionAb.add(x); //{3}
模拟交集操作
模拟交集操作需要创建一个辅助函数,来生成包含
setA
和setB
都有的元素的新集合(行{1}
)。代码如下:let intersection = function(setA, setB) { let intersectionSet = new Set; for (let x of setA) { if (setB.has(x)) { //{1} intersectionSet.add(x); } } return intersectionSet;};let intersectionAB = intersection(setA, setB);
交集可以用更简单的语法实现,代码如下:
intersectionAb = new Set([x for (x of setA) if (setB.has(x))]);
这和
intersection
函数的效果完全一样。目前只有Firefox支持简化的语法,但在所有支持ES6的现代浏览器中都可以执行
intersection
函数。模拟差集操作
交集操作创建的集合包含
setA
和setB
都有的元素,差集操作创建的集合包含的则是setA
有而setB
没有的元素。看下面的代码:let difference = function(setA, setB) { let differenceSet = new Set; for (let x of setA) { if (!setB.has(x)) { //{1} differenceSet.add(x); } } return differenceSet;};let differenceAB = difference(setA, setB);
intersection
函数和difference
函数只有行{1}
不同,因为差集中只添加setA
有而setB
没有的元素。差集也可以用更简单的语法实现,代码如下:
differenceAB = new Set([x for (x of setA) if (!setB.has(x))]);
目前只有Firefox支持简化的语法,但在所有支持ES6的现代浏览器中都可以执行
difference
函数。