gitee.com/sy_183/go-common@v1.0.5-0.20231205030221-958cfe129b47/lifecycle.v2/future/future.go (about) 1 package future 2 3 import ( 4 "gitee.com/sy_183/go-common/lock" 5 "sync" 6 "sync/atomic" 7 ) 8 9 type Future[V any] interface { 10 Complete(value V) 11 } 12 13 type WaitableFuture[V any] interface { 14 Future[V] 15 16 Wait() V 17 } 18 19 type NopFuture[V any] struct{} 20 21 func (f NopFuture[V]) Complete(value V) {} 22 23 type ChanFuture[V any] chan V 24 25 func (c ChanFuture[V]) Complete(value V) { c <- value } 26 func (c ChanFuture[V]) Wait() V { return <-c } 27 28 type WaiterFuture[V any] struct { 29 waiter sync.WaitGroup 30 value V 31 once atomic.Bool 32 } 33 34 func NewWaiterFuture[V any]() *WaiterFuture[V] { 35 future := new(WaiterFuture[V]) 36 future.waiter.Add(1) 37 return future 38 } 39 40 func (w *WaiterFuture[V]) Complete(value V) { 41 if w.once.CompareAndSwap(false, true) { 42 w.value = value 43 w.waiter.Done() 44 } 45 } 46 47 func (w *WaiterFuture[V]) Wait() V { 48 w.waiter.Wait() 49 return w.value 50 } 51 52 type CallbackFuture[V any] func(value V) 53 54 func (f CallbackFuture[V]) Complete(value V) { 55 f(value) 56 } 57 58 type AtomicCallbackFuture[V any] struct { 59 callback atomic.Pointer[func(value V)] 60 value atomic.Pointer[V] 61 once atomic.Bool 62 done atomic.Bool 63 } 64 65 func NewAtomicCallbackFuture[V any](callback func(value V)) *AtomicCallbackFuture[V] { 66 future := new(AtomicCallbackFuture[V]) 67 if callback != nil { 68 future.callback.Store(&callback) 69 } 70 return future 71 } 72 73 func (f *AtomicCallbackFuture[V]) Complete(value V) { 74 if f.once.CompareAndSwap(false, true) { 75 f.value.Store(&value) 76 if callback := f.callback.Load(); callback != nil && f.done.CompareAndSwap(false, true) { 77 (*callback)(value) 78 } 79 } 80 } 81 82 func (f *AtomicCallbackFuture[V]) SetCallback(callback func(value V)) { 83 f.callback.Store(&callback) 84 if value := f.value.Load(); value != nil && f.done.CompareAndSwap(false, true) { 85 callback(*value) 86 } 87 } 88 89 type Futures[V any] []Future[V] 90 91 func (fs Futures[V]) Complete(value V) { 92 for _, future := range fs { 93 future.Complete(value) 94 } 95 } 96 97 type SyncFutures[V any] struct { 98 futures Futures[V] 99 sync.Mutex 100 } 101 102 func NewSyncFutures[V any]() *SyncFutures[V] { 103 return new(SyncFutures[V]) 104 } 105 106 func (f *SyncFutures[V]) Append(future Future[V]) { 107 if future == nil { 108 return 109 } 110 lock.LockDo(f, func() { f.futures = append(f.futures, future) }) 111 } 112 113 func (f *SyncFutures[V]) LoadAndReset() Futures[V] { 114 return lock.LockGet(f, func() (futures Futures[V]) { 115 futures = append(futures, f.futures...) 116 f.futures = f.futures[:0] 117 return 118 }) 119 } 120 121 type WaitGroupFuture[V any] struct { 122 wg sync.WaitGroup 123 } 124 125 func (f *WaitGroupFuture[V]) Add(delta int) *WaitGroupFuture[V] { 126 f.wg.Add(delta) 127 return f 128 } 129 130 func (f *WaitGroupFuture[V]) Complete(value V) { 131 f.wg.Done() 132 } 133 134 func (f *WaitGroupFuture[V]) Wait() { 135 f.wg.Wait() 136 }