# All about Set and WeakSet in JavaScript ?

In this article, we will learn about `Set` and `WeakSeat.`

## Set

A JavaScript Set is a collection of unique values of any type, whether they are primitive values or object references. A `Set` can only contain unique values, meaning that duplicate values are automatically removed.

The `Set` is also an ordered collection of elements. It means the retrieval order of the elements will be the same as that of the insertion order.

### To create a new Set

```javascript
const set = new Set();
console.log(set);
// Set(0) {}
```

For Example:

```javascript
const letters = new Set(["a","b","c"]);
console.log(letters );
// Set(3) { 'a', 'b', 'c' }
```

## Essential Set Methods

### To add elements to the `Set`

Adds a new element to the Set

```javascript
const letters  = new Set(["a","b","c"]);
letters.add("d")
letters.add("e")
console.log(letters);
// Set(5) { 'a', 'b', 'c', 'd', 'e' }
```

### Checking if a Value Exists

Returns true if a value exists in the Set Otherwise it returns false.

```javascript
const letters  = new Set(["a","b","c"]);
console.log(letters.has("c")); // true
console.log(letters.has("d")); // false
```

### To Check Size

You can check the number of elements in a `Set` using the `size` property:

```javascript
const letters  = new Set(["a","b","c"]);
console.log(letters.size);  // 3
```

### Iterating Over Values

You can iterate over the values in a `Set` using the `forEach` method or by using a `for...of` loop

```javascript
const letters  = new Set(["a","b","c"]);
letters.forEach((value) => {
  console.log(value);
});
// a
// b
// c

for (const value of letters  ) {
  console.log(value);
}
// a
// b
// c
```

### using values()

The `Set` has a method called, `values()` which returns a `SetIterator` to get all the values.

```javascript
const letters  = new Set(["a","b","c"]);
console.log(letters.values());  // [Set Iterator] { 'a', 'b', 'c' }


console.log(letters.keys());   // [Set Iterator] { 'a', 'b', 'c' }
console.log(letters.entries()); //  [Set Entries] { [ 'a', 'a' ], [ 'b', 'b' ], [ 'c', 'c' ] }
```

### To Remove a Value

```javascript
const letters  = new Set(["a","b","c"]);
letters.delete("c");
console.log(letters); // Set(2) { 'a', 'b' }
```

### To Clear the Set

```javascript
const letters  = new Set(["a","b","c"]);
letters.clear();
console.log(letters);  // Set(0) {}
```

**A** `Set` **can have elements of any type, even objects.**

```javascript
// Create a person object
const person = {
   'name': 'Alex',
   'age': 32
 };

// Let us create a set and add the object to it
const personSet = new Set();
personSet.add(person);
console.log(personSet);
//  Set(1) { { name: 'Alex', age: 32 } }
```

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1684469457130/e467b2c1-3f33-4c89-9e83-2ae2d693dea6.png align="center")

## **Convert Set to an array**

```javascript
const letters  = new Set(["a","b","c"]);
const arr = [...letters];   // spread operator
const arr1= Array.from(letters); // Array.from()
console.log(arr);  //  [ 'a', 'b', 'c' ]
console.log(arr1);  //  [ 'a', 'b', 'c' ]
```

Output,

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1684469700152/e1035fce-e242-4985-8bbc-200ed4830b48.png align="center")

# **Set Operations**

Now it is easy to perform set operations like, `union`, `intersection`, `diference`, `superset`, `subset` etc with `Set` and array together. Let us take these two sets to perform these operations.

```javascript
const A = new Set([1, 2, 3]);
const B = new Set([3, 4, 5]);
```

### **Union**

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1684470865122/b3ee3239-4c6e-4939-90db-71cf5ce2e1b8.png align="center")

![](https://www.probabilitycourse.com/images/chapter1/intersection_b.png align="center")

```javascript
// Union
const union = new Set([...first, ...second]);
console.log('Union:', union);
// Union: Set(5) {1, 2, 3, 4, 5}
```

### **Intersection**

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1684470980959/babd05af-7c2e-4588-a33e-3156ef50f4c3.png align="center")

```javascript
// Intersection
const intersection = new Set([...first].filter(elem => second.has(elem)));
console.log('Intersection:', intersection);
// Intersection: Set(1) {3}
```

### **Difference**

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1684471029948/e56fc9c0-8b03-4b9b-b98a-d6279975a455.jpeg align="center")

```javascript
// Difference
const difference = new Set([...first].filter(elem => !second.has(elem)));
// Difference: Set(2) {1, 2}
```

### **Superset**

![](https://d1whtlypfis84e.cloudfront.net/guides/wp-content/uploads/2018/08/03120034/subset.jpg align="center")

```javascript
// Is a superset?
const isSuperset = (set, subset) => {
  for (let elem of subset) {
     if (!set.has(elem)) {
         return false;
     }
  }
  return true;
}
console.log('Is Superset?', isSuperset(first, second));
// Is Superset? false
```

## **Weak Set**

In javascript, a `Set` is a collection of unique and ordered elements. Just like Set, `WeakSet` is also a collection of unique and ordered elements with some key differences:

`WeakSet` can only store object references. Primitive values like numbers or strings cannot be stored in a `WeakSet`. for Example

```javascript
const newSet = new Set([4, 5, 6, 7]);
console.log(newSet);// Outputs Set {4,5,6,7}

const newSet1 = new WeakSet([3, 4, 5]);
console.log((newSet1)); //  Throws an error
```

```javascript
let obj1 = {message:"Hello world"};
const newSet2=new WeakSet(obj1);
console.log(newSet2); 
```

output

![](https://cdn.hashnode.com/res/hashnode/image/upload/v1684478967100/a74a78ba-f7bd-45f9-abf2-b29759c9460b.jpeg align="center")

Unlike `Set`, `WeakSet` holds weak references to the objects it contains. This means that if there are no other references to an object stored in a `WeakSet`, the object may be garbage collected by the JavaScript engine.

`WeakSet` can only contain unique object references. If you attempt to add the same object reference multiple times, it will be stored only once.

`WeakSet` does not provide methods for iterating over its elements or retrieving all the values stored in it. This is because the weak references it holds do not allow for predictable iteration.

`WeakSet` has a limited set of methods compared to `Set`. It only provides the `add`, `delete`, and `has` methods for adding, removing, and checking the presence of object references, respectively.

```javascript
const weakSet = new WeakSet();

const obj1 = { name: 'John' };
const obj2 = { name: 'Jane' };

weakSet.add(obj1);
weakSet.add(obj2);

console.log(weakSet.has(obj1)); // Output: true

weakSet.delete(obj2);

console.log(weakSet.has(obj2)); // Output: false
```
