In-depth Understanding of ES6 007 [Study Notes]

Set and Map Collections. In JS, there is an `in` operator that can determine if a property exists in an object without needing to read the object's value, returning true if it exists. However, the `in` operator also checks the object's prototype chain, so using this method is only relatively safe when the object's prototype is null. Set Collection: `let set = new Set()` `set.add(5)` `set.add("5")` `console.log(s…`

Set Collection and Map Collection

In JS, there is an in operator, which can determine if a property exists in an object without needing to read the object's value; if it exists, it returns true. However, the `in` operator also checks the object's prototype, so this method is only reliable when the object's prototype is null.

Set Collection

let set = new Set()
set.add(5)
set.add("5")
console.log(set.size) // 2
const key1={},key2={}
set.add(key1)
set.add(key1)
console.log(set.size) // 4
// 传入相同值实际上会被忽略
let set1 = new Set(1,2,3,4,5,5,5,5)
console.log(set.size) //5
set1.has(5) //true
set1.has(6) // false
set1.delete(5)
set1.has(5) //false

set1.clear() // 所有元素被清除

A Set collection does not perform forced type conversion on stored values; the number 5 and the string "5" can exist as two independent elements (the engine uses `Object.is()` as mentioned before for judgment). If multiple objects are added to a Set, they remain independent of each other.

Set Collection's forEach Method

The callback function of the forEach() method accepts the following 3 parameters

  • The next index position in the Set collection
  • A value identical to the first parameter
  • The Set collection being iterated over itself

The `forEach()` method of a Set collection has a peculiar difference from the `forEach()` method in arrays: the values of the first two parameters of the callback function are actually the same. In fact, the `forEach()` callback function of a Map collection also accepts 3 parameters, where the first two are the value and the key, respectively.

The second parameter of the `forEach` function is the same as for arrays; if `this` needs to be used within the callback function, it can be passed as the second argument.

let set = new Set([1,2])
let processor = {
  output(value){
    console.log(value)
  },
  process(dataSet){
    // 这里使用箭头函数,就无须再将this作为第二个参数传入回调函数了
    dataSet.forEach(function(value){
      this.output(value)
    },this)
  }
}
processor.process(set)

Although Set collections are more suitable for tracking multiple values and each element in the collection can be manipulated using the `forEach()` method, you cannot access elements in a collection directly by index like you would with array elements. If necessary, it's best to convert the Set collection into an array first.

let set = new Set([1,2,3,3,3,4,5])
arrray = [...set]
console.log(array) // [1,2,3,4,5] 去重

function eliminateDuplicates(items){
  return [...new Set(items)]
}
let numbers = [1,2,3,3,3,4,5],
noDuplicates = eliminateDuplicates(numbers);
console.log(noDuplicates); // [1,2,3,4,5]

Weak Set Collection

Storing an object in a Set instance is similar to storing it in a variable: as long as a reference exists in the Set instance, the garbage collector cannot free the object's memory space. Thus, the Set type mentioned earlier can be considered a Set collection with strong references. As follows:

let set = new Set(),
key = {};
set.add(key);
console.log(set.size) // 1
// 移除原始引用
key = null;
console.log(set.size) // 1
// 重新取回原始引用
key = [...set][0]

For example, if we use this Set to store a DOM object, and a script removes this DOM element, the Set will still retain this reference (causing a memory leak). Therefore, ES6 introduced the WeakSet collection. A WeakSet can only store weak references to objects and cannot store primitive values; if a weak reference in the collection is the object's only reference, it will be garbage collected and its memory released.

// 集合支持add()/has()/delete()
let set = new WeakSet(),key = {};
// 向集合添加对象
set.add(key);
console.log(set.has(key)); // true
set.delete(key);
console.log(set.has(key)); // false
let key1 = {}, key2 = {};
set = new WeakSet([key1,key2]) // 如果数组中包含其非对象值,程序会抛出错误
console.log(set.has(key1)) // true
console.log(set.has(key2)) // true

// #################
// 移除对象key的最后一个强引用(Weak Set中的引用也自动移除)
let set = new Set(),
key = {};
set.add(key);
console.log(set.has(key)) // true
// 移除对象key的最后个强引用(Weak Set中的引用也自动移除)
key = null;
// 这段代码执行过后,就无法访问WeakSet中的key的引用了,由于我们需要向has方法传递一个强引用才能验证这个弱引用是否已被移除了。
  • WeakSet
  • Passing non-object arguments to the add/has/delete methods will cause the program to throw an error.
  • Not iterable; cannot use `for-of` loops.
  • Does not expose any iterators (`keys` and `values`), so its contents cannot be inspected by the program itself.
  • Does not support `forEach`.
  • Does not support `size`.

Map

  • set
  • get
  • has
  • delete
  • clear
  • size property

Initialization Method

let map = new Map([["name","Nicholas"],["age",23]])

forEach((value,key,ownerMap)=>{}, binding context)

let map = new Map([["name","Nicholas"],["age",23]])
map.forEach(function(value,key,ownerMap){
   console.log(key+" "+value);
   console.log(ownerMap === map)
})

WeakMap

The principle is consistent with WeakSet: keys are weak references to objects, and keys can only store objects.

let map = new WeakMap(),
element = document.querySelector('.element');
map.set(element,"Original")
let value = map.get(element)
console.log(value) // Original
// 移除element元素
element.parentNode.removeChild(element);
element = null;
// 此时Weak Map集合为空

Private Object Data

function Person(name){
  this._name = name;
}
Person.prototype.getName = function(){
  return this._name;
}
// 约定前缀为下划线的属性为私有属性,不允许在对象实例外改变这个属性。例如,只能通过getName()方法读取this._name,所以它也有可能在无意间被覆写

ES5 can create an object with nearly true private data using the following pattern:

var Person = (function(){
  var privateData = {},
  privateId = 0;
  function Person(name){
    Object.defineProperty(this,"_id",{value:privateId++})
    privateData[this._id] = {
      name:name
    }
  }
  Person.prototype.getName = function(){
    return privateData[this._id].name
  }
  return Person
}())

When the `Person` constructor is called, the value of the `_id` property is incremented by 1. This property is non-enumerable, non-configurable, and non-writable. The biggest problem with the above code is the inability to actively manage it; since it's impossible to know when an object instance is destroyed, the data in `privateData` will never disappear. However, using a WeakMap collection can solve this problem.

let Person = (function(){
  let privateData = new WeakMap();
  function Person(name){
    privateData.set(this,{name:name})
  }
  Person.prototype.getName = function(){
    return privateData.get(this).name
  }
  return Person
}())
// 只要对象实例被销毁,相关信息也会被销毁,从而保证了信息的私有性

主题测试文章,只做测试使用。发布者:Walker,转转请注明出处:https://walker-learn.xyz/archives/4333

(0)
Walker的头像Walker
上一篇 Nov 25, 2025 14:00
下一篇 Nov 25, 2025 12:00

Related Posts

  • In-depth Understanding of ES6 004 [Study Notes]

    Extending object functionality
    Ordinary objects: objects that possess all default internal behaviors of a JavaScript object.
    Exotic objects: objects that possess certain internal behaviors that deviate from the default.
    Standard objects: objects defined in the ES6 specification, such as Array/Date.
    Built-in objects: objects that exist in the JavaScript execution environment when the script begins execution; all standard objects are built-in objects.
    Object literal syntax extensions:
    Shorthand for property initializers: when an object's property has the same name as a local variable, there's no need to write the colon and value.
    Shorthand syntax for object methods...

    Personal Mar 8, 2025
    1.4K00
  • Go Engineer's Comprehensive Course 017: Learning Notes

    Introduction to Rate Limiting, Circuit Breaking, and Degradation (with Sentinel Practical Application)
    Based on the key video points from Chapter 3 (3-1 to 3-9) of the courseware, this guide compiles a service protection introduction for beginners, helping them understand "why rate limiting, circuit breaking, and degradation are needed," and how to quickly get started with Sentinel.
    Learning Path at a Glance
    3-1 Understanding Service Avalanche and the Background of Rate Limiting, Circuit Breaking, and Degradation
    3-2 Comparing Sentinel and Hystrix to clarify technology selection
    3-3 Sen...

    Personal Nov 25, 2025
    28100
  • Go Engineer Systematic Course 009 [Study Notes]

    Other features: Personal Center, Favorites, Manage shipping addresses (add, delete, modify, query), Messages. Copy inventory_srv --> userop_srv. Query and replace all inventory. Elasticsearch Deep Dive Document. 1. What is Elasticsearch. Elasticsearch is a distributed, RESTful search and analytics engine built on Apache Lucene, capable of quickly…

    Personal Nov 25, 2025
    36700
  • In-depth Understanding of ES6 008 [Study Notes]

    Iterators (Iterator) and Generators (Generator) are new features indispensable for efficient data processing. You will also find iterators present in other language features: the new for-of loop, the spread operator (...), and even asynchronous programming can use iterators. An iterator is a special object that has proprietary interfaces specifically designed for the iteration process. All iterator objects have a next() method, and each call returns a result pair...

    Personal Mar 8, 2025
    1.2K00
  • Go Engineering Systematic Course 003 [Study Notes]

    grpc grpc grpc-go grpc seamlessly integrates protobuf protobuf. For those of you accustomed to using JSON and XML data storage formats, I believe most have never heard of Protocol Buffer. Protocol Buffer is actually a lightweight & efficient structured data storage format developed by Google, and its performance is truly much, much stronger than JSON and XML! protobuf…

    Personal Nov 25, 2025
    29800
EN
简体中文 繁體中文 English