Categories
Modern JavaScript

Best of Modern JavaScript — Sets and WeakSets

Spread the love

Since 2015, JavaScript has improved immensely.

It’s much more pleasant to use it now than ever.

In this article, we’ll look at sets and WeakSets.

Set API

The Set API has various methods we can use to let us manipulate it.

The constructor lets us pass in an iterable object and create a set from it.

For instance, we can write:

const set = new Set([1, 2, 3]);

to create a set from an array.

The Set.prototype.add method takes a value and appends it to the set.

It returns the set with the new entry.

Set.prototype.has takes a value and returns true if it’s in the set and false otherwise.

The Set.prototype.delete method takes a value and lets us remove it.

It returns true if it’s deleted and false otherwise.

The Set.prototype.size getter returns the number of items in the set.

The Set.prototype.clear method lets us remove all items from a set.

Set.prototype.values is a method that returns all values of a set as an iterator.

Set.prototype[Symbol.iterator] returns an iterable object that lets us iterate over a set.

The Set.prototype.forEach let takes a callback with the signature, (value, key, collection) as the signature, and runs it for each item in the set,

value has the set value.

key has the same value as value .

The collection is the set itself.

The 2nd argument is the value of this we use in the callback.

Sets also have the Set.prototype.entries method to return an iterable object with each entry being a key-value array.

The key and value are the same.

The Set.prototype.keys method returns us an iterable object with the keys, which is the same as the values.

WeakSet

A WeakSet is a set that doesn’t prevent its elements from being garbage collected.

It works like WeakMaps and doesn’t allow iteration, looping, or clearing.

There isn’t many uses cases for WeakSets.

We can add objects to them and then get them with the reference.

So we can write:

const weakSet = new WeakSet();

const obj = {};
weakSet.add(obj);
const hasObj = weakSet.has(obj);

We pass in a map and then check for its value with has .

We can only pass objects into a WeakSet.

We’ll get a TypeError if we try to pass in a primitive value.

Also, we can use WeakSets to allow us to run a method on a given class instance.

For example, we can write:

const bars = new WeakSet();

class Bar {
  constructor() {
    bars.add(this);
  }

  method() {
    if (!bars.has(this)) {
      throw new TypeError('not a bar instance');
    }
  }
}

We add the Bar instance to the bars WeakSet in the constructor.

Then in the method method, we check if the Bar instance if part of the WeakSet with has .

If it’s not, then we throw an error.

This prevents the method from being run on anything other than Bar instances.

WeakSet API

WeakSets has a simple API with 3 methods and works like their Set equivalents.

WeakSet.prototype.add takes a value as an argument and lets us add an entry to it.

WeakSet.prototype.has takes a value and returns true if the entry exists and false otherwise.

WeakSet.prototype.delete takes a value and removes the element from the WeakSet.

Conclusion

Sets let us add items without duplicating.

WeakSets let us hold items that can be garbage collected when they aren’t used.

Leave a Reply

Your email address will not be published.

If you like the content of this blog, subscribe to my email list to get exclusive articles not available to anyone else.