DEV Community

Tomasz Kula
Tomasz Kula

Posted on • Originally published at upbeat.dev

How distinct is distinctUntilChanged?

If you have been working with RxJS, you might have heard about distinctUntilChanged() operator 🔥

Let's have a quick peek into the official docs to see how it works:

Returns an Observable that emits all items emitted by the source Observable that are distinct by comparison from the previous item.

So in short, if the source stream emits:

a-a-b
Enter fullscreen mode Exit fullscreen mode

You get just

a---b
Enter fullscreen mode Exit fullscreen mode

There is a catch, though. By default, the operator will compare values using the === operator.

This will work fine for primitive values like strings or numbers which are compared by value, but will not work for stuff like arrays or objects which are compared by reference.

'a' === 'a' // true
1 === 1     // true
{} === {}   // false
[] === []   // false
Enter fullscreen mode Exit fullscreen mode

So any time you are working with objects streams, you should strongly consider providing your own compare function to the distinctUntilChanged() operator.

const source = of({ id: 1 }, { id: 1 }, { id: 2 });

// ❌ does not work, because values are compared with ===
source.pipe(
  distinctUntilChanged()
).subscribe(console.log);
// logs { id: 1 } { id: 1 } { id: 2 }

// 🔥 it works, because we provide a custom compare function
source.pipe(
  distinctUntilChanged((prev, next) => prev.id === next.id)
).subscribe(console.log);
// logs { id: 1 } { id: 2 }
Enter fullscreen mode Exit fullscreen mode

Live demo

Hope you're having a great one, and I'll see you for more 60 Seconds posts in the future 🥳

Top comments (0)