Sets

一个set是一个集合,其中的值都是唯一的(重复的会被忽略)。

set的API与map很相似。add(..)方法(有点讽刺地)取代了set(..),而且没有get(..)方法。

考虑如下代码:

  1. var s = new Set();
  2. var x = { id: 1 },
  3. y = { id: 2 };
  4. s.add( x );
  5. s.add( y );
  6. s.add( x );
  7. s.size; // 2
  8. s.delete( y );
  9. s.size; // 1
  10. s.clear();
  11. s.size; // 0

Set(..)构造器形式与Map(..)相似,它可以接收一个可迭代对象,比如另一个set或者一个值的数组。但是,与Map(..)期待一个 记录 的列表(键/值数组的数组)不同的是,Set(..)期待一个 的列表(值的数组):

  1. var x = { id: 1 },
  2. y = { id: 2 };
  3. var s = new Set( [x,y] );

一个set不需要get(..),因为你不会从一个set中取得值,而是使用has(..)测试一个值是否存在:

  1. var s = new Set();
  2. var x = { id: 1 },
  3. y = { id: 2 };
  4. s.add( x );
  5. s.has( x ); // true
  6. s.has( y ); // false

注意: has(..)中的比较算法与Object.is(..)(见第六章)几乎完全相同,除了-00被视为相同而非不同。

Set 迭代器

set和map一样拥有相同的迭代器方法。set的行为有所不同,但是与map的迭代器的行为是对称的。考虑如下代码:

  1. var s = new Set();
  2. var x = { id: 1 },
  3. y = { id: 2 };
  4. s.add( x ).add( y );
  5. var keys = [ ...s.keys() ],
  6. vals = [ ...s.values() ],
  7. entries = [ ...s.entries() ];
  8. keys[0] === x;
  9. keys[1] === y;
  10. vals[0] === x;
  11. vals[1] === y;
  12. entries[0][0] === x;
  13. entries[0][1] === x;
  14. entries[1][0] === y;
  15. entries[1][1] === y;

keys()values()迭代器都会给出set中唯一值的列表。entries()迭代器给出记录数组的列表,记录数组中的两个元素都是唯一的set值。一个set的默认迭代器是它的values()迭代器。

一个set天生的唯一性是它最有用的性质。例如:

  1. var s = new Set( [1,2,3,4,"1",2,4,"5"] ),
  2. uniques = [ ...s ];
  3. uniques; // [1,2,3,4,"1","5"]

set的唯一性不允许强制转换,所以1"1"被认为是不同的值。