在 Eloquent JavaScript 的第 4 章中,一组值是通过创建一个对象并将值存储为属性名称、分配任意值(例如 true)作为属性值来创建的。要检查该值是否已包含在集合中,使用 in
运算符:
var set = {};
if (!'Tom' in set) {
set.Tom = true;
}
这是惯用的 JavaScript 吗?使用数组不是更好吗?
var set = [];
if (!'Tom' in set) {
set.push = 'Tom';
}
最佳答案
Sets现在在 ES2015(又名 ES6,即 ECMAScript 6)中可用。自 2015 年 6 月以来,ES6 一直是 JavaScript 的当前标准。
ECMAScript 6 has the data structure Set which works for arbitrary values, is fast and handles NaN correctly. -Axel Rauschmayer, Exploring ES6
前两个示例来自 Axel Rauschmayer's书Exploring ES6 :
Managing single elements:
> let set = new Set();
> set.add('red')
> set.has('red')
true
> set.delete('red')
true
> set.has('red')
false
Determining the size of a Set and clearing it:
> let set = new Set();
> set.add('red')
> set.add('green')
> set.size
2
> set.clear();
> set.size
0
我会查看 Exploring ES6如果您想了解有关 JavaScript 中的集合的更多信息。该书可在线免费阅读,但如需支持作者Dr. Axel Rauschmayer您可以花大约 30 美元购买这本书。
如果你现在想使用 Sets 和 ES6,你可以使用 Babel 、ES6 到 ES5 的转译器及其 polyfill。
编辑:截至 2017 年 6 月 6 日,大多数主要浏览器的最新版本(IE 11 除外)都支持完整的 Set。这意味着如果你不想支持旧的浏览器,你可能不需要 babel。如果您想查看不同浏览器(包括您当前的浏览器)的兼容性,请检查 Kangax's ES6 compatibility table .
编辑:
只是对初始化的澄清。集合可以在其构造函数中采用任何同步可迭代对象。这意味着它们不仅可以接受数组,还可以接受字符串和迭代器。以集合的以下数组和字符串初始化为例:
const set1 = new Set(['a','a','b','b','c','c']);
console.log(...set1);
console.log(set1.size);
const set2 = new Set("aabbcc");
console.log(...set2);
console.log(set2.size);
数组和字符串的输出是一样的。注意 ...set1
是 spread syntax .似乎 iterable 的每个元素都被一个一个地添加到集合中,因此由于数组和字符串都具有相同的元素,并且由于元素的顺序相同,因此集合的创建方式相同。关于集合的另一件需要注意的事情是,在迭代它们时,迭代顺序遵循元素插入集合的顺序。下面是一个迭代集合的例子:
const set1 = new Set(['a','a','b','b','c','c']);
for(const element of set1) {
console.log(element);
}
由于您可以使用任何可迭代对象来初始化集合,您甚至可以使用 generator function 中的迭代器.下面是产生相同输出的两个这样的迭代器初始化示例:
// a simple generator example
function* getLetters1 () {
yield 'a';
yield 'a';
yield 'b';
yield 'b';
yield 'c';
yield 'c';
}
// a somewhat more commonplace generator example
// with the same output as getLetters1.
function* getLetters2 (letters, repeatTimes) {
for(const letter of letters) {
for(let i = 0; i < repeatTimes; ++i) {
yield letter;
}
}
}
console.log("------ getLetters1 ------");
console.log(...getLetters1());
const set3 = new Set(getLetters1());
console.log(...set3);
console.log(set3.size);
console.log("------ getLetters2 ------");
console.log(...getLetters2('abc', 2));
const set4 = new Set(getLetters2('abc', 2));
console.log(...set4);
console.log(set4.size);
这些示例的生成器函数可以只写成不重复,但是如果生成器函数更复杂并且只要以下不会对性能产生太大的负面影响,您可以使用 Set 方法来帮助仅从不重复的生成器。
如果您想在不阅读 Rauschmayer 博士书中的章节的情况下了解更多关于集合的信息,您可以查看 MDN docs on Set . MDN 还有更多迭代集合的示例,例如使用 forEach
和使用 .keys
、.values
和 .entries
方法。 MDN也有集合并集、集合交集、集合差集、对称集差集、集合超集检查等例子。希望这些操作中的大部分都可以在 JavaScript 中使用,而无需构建您自己的支持它们的函数。其实还有this TC39 proposal for new Set methods如果提案达到第 4 阶段,希望在未来的某个时间点将以下方法添加到 JavaScript 中的 Set:
- Set.prototype.intersection(iterable) - method creates new Set instance by set intersection operation.
- Set.prototype.union(iterable) - method creates new Set instance by set union operation.
- Set.prototype.difference(iterable) - method creates new Set without elements present in iterable.
- Set.prototype.symmetricDifference(iterable) - returns Set of elements found only in either this or in iterable.
- Set.prototype.isSubsetOf(iterable)
- Set.prototype.isDisjointFrom(iterable)
- Set.prototype.isSupersetOf(iterable)
关于javascript - 在 JavaScript 中创建集合的方法?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8363564/