You can not select more than 25 topics Topics must start with a chinese character,a letter or number, can include dashes ('-') and can be up to 35 characters long.

token_pool.go 915 B

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960
  1. package sync2
  2. import "sync"
  3. type TokenPool[T any] struct {
  4. tokens []T
  5. cond *sync.Cond
  6. closed bool
  7. }
  8. func NewTokenPool[T any]() *TokenPool[T] {
  9. return &TokenPool[T]{
  10. tokens: make([]T, 0),
  11. cond: sync.NewCond(new(sync.Mutex)),
  12. }
  13. }
  14. func NewTokenPoolWithTokens[T any](tokens ...T) *TokenPool[T] {
  15. b := NewTokenPool[T]()
  16. b.tokens = append(b.tokens, tokens...)
  17. return b
  18. }
  19. func (b *TokenPool[T]) Take() (T, bool) {
  20. b.cond.L.Lock()
  21. defer b.cond.L.Unlock()
  22. var ret T
  23. if b.closed {
  24. return ret, false
  25. }
  26. if len(b.tokens) == 0 {
  27. b.cond.Wait()
  28. if len(b.tokens) == 0 {
  29. return ret, false
  30. }
  31. }
  32. ret = b.tokens[0]
  33. b.tokens = b.tokens[1:]
  34. return ret, true
  35. }
  36. func (b *TokenPool[T]) Put(t T) {
  37. b.cond.L.Lock()
  38. b.tokens = append(b.tokens, t)
  39. b.cond.L.Unlock()
  40. b.cond.Signal()
  41. }
  42. func (b *TokenPool[T]) Close() {
  43. b.cond.L.Lock()
  44. b.closed = true
  45. b.cond.L.Unlock()
  46. b.cond.Broadcast()
  47. }