@@ -12,6 +12,10 @@ import * as Result from "../Result.js"
1212
1313const constImmediate = { immediate : true }
1414
15+ const notifyListener = ( listener : ( ) => void ) : void => {
16+ listener ( )
17+ }
18+
1519type TypeId = "~effect-atom/atom/Registry"
1620const TypeId : TypeId = "~effect-atom/atom/Registry" as const
1721
@@ -287,11 +291,11 @@ class Node<A> {
287291 parents : Array < Node < any > > = [ ]
288292 previousParents : Array < Node < any > > | undefined
289293 children : Array < Node < any > > = [ ]
290- listeners : Array < ( ) => void > = [ ]
294+ listeners : Set < ( ) => void > = new Set ( )
291295 skipInvalidation = false
292296
293297 get canBeRemoved ( ) : boolean {
294- return ! this . atom . keepAlive && this . listeners . length === 0 && this . children . length === 0 &&
298+ return ! this . atom . keepAlive && this . listeners . size === 0 && this . children . length === 0 &&
295299 this . state !== 0
296300 }
297301
@@ -352,7 +356,7 @@ class Node<A> {
352356 this . invalidateChildren ( )
353357 }
354358
355- if ( this . listeners . length > 0 ) {
359+ if ( this . listeners . size > 0 ) {
356360 if ( batchState . phase === BatchPhase . collect ) {
357361 batchState . notify . add ( this )
358362 } else {
@@ -397,7 +401,7 @@ class Node<A> {
397401
398402 if ( batchState . phase === BatchPhase . collect ) {
399403 batchState . stale . push ( this )
400- } else if ( this . atom . lazy && this . listeners . length === 0 && ! childrenAreActive ( this . children ) ) {
404+ } else if ( this . atom . lazy && this . listeners . size === 0 && ! childrenAreActive ( this . children ) ) {
401405 this . invalidateChildren ( )
402406 this . skipInvalidation = true
403407 } else {
@@ -418,9 +422,7 @@ class Node<A> {
418422 }
419423
420424 notify ( ) : void {
421- for ( let i = 0 ; i < this . listeners . length ; i ++ ) {
422- this . listeners [ i ] ( )
423- }
425+ this . listeners . forEach ( notifyListener )
424426
425427 if ( batchState . phase === BatchPhase . commit ) {
426428 batchState . notify . delete ( this )
@@ -441,7 +443,7 @@ class Node<A> {
441443
442444 remove ( ) {
443445 this . state = NodeState . removed
444- this . listeners = [ ]
446+ this . listeners . clear ( )
445447
446448 if ( this . lifetime === undefined ) {
447449 return
@@ -464,14 +466,8 @@ class Node<A> {
464466 }
465467
466468 subscribe ( listener : ( ) => void ) : ( ) => void {
467- this . listeners . push ( listener )
468- return ( ) => {
469- const index = this . listeners . indexOf ( listener )
470- if ( index !== - 1 ) {
471- this . listeners [ index ] = this . listeners [ this . listeners . length - 1 ]
472- this . listeners . pop ( )
473- }
474- }
469+ this . listeners . add ( listener )
470+ return ( ) => this . listeners . delete ( listener )
475471 }
476472}
477473
@@ -485,7 +481,7 @@ function childrenAreActive(children: Array<Node<any>>): boolean {
485481 while ( current !== undefined ) {
486482 for ( let i = 0 , len = current . length ; i < len ; i ++ ) {
487483 const child = current [ i ]
488- if ( ! child . atom . lazy || child . listeners . length > 0 ) {
484+ if ( ! child . atom . lazy || child . listeners . size > 0 ) {
489485 return true
490486 } else if ( child . children . length > 0 ) {
491487 if ( stack === undefined ) {
0 commit comments