bool.go 1.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071
  1. // Package abool provides atomic Boolean type for cleaner code and
  2. // better performance.
  3. package abool
  4. import "sync/atomic"
  5. // New creates an AtomicBool with default set to false.
  6. func New() *AtomicBool {
  7. return new(AtomicBool)
  8. }
  9. // NewBool creates an AtomicBool with given default value.
  10. func NewBool(ok bool) *AtomicBool {
  11. ab := New()
  12. if ok {
  13. ab.Set()
  14. }
  15. return ab
  16. }
  17. // AtomicBool is an atomic Boolean.
  18. // Its methods are all atomic, thus safe to be called by multiple goroutines simultaneously.
  19. // Note: When embedding into a struct one should always use *AtomicBool to avoid copy.
  20. type AtomicBool int32
  21. // Set sets the Boolean to true.
  22. func (ab *AtomicBool) Set() {
  23. atomic.StoreInt32((*int32)(ab), 1)
  24. }
  25. // UnSet sets the Boolean to false.
  26. func (ab *AtomicBool) UnSet() {
  27. atomic.StoreInt32((*int32)(ab), 0)
  28. }
  29. // IsSet returns whether the Boolean is true.
  30. func (ab *AtomicBool) IsSet() bool {
  31. return atomic.LoadInt32((*int32)(ab))&1 == 1
  32. }
  33. // IsNotSet returns whether the Boolean is false.
  34. func (ab *AtomicBool) IsNotSet() bool {
  35. return !ab.IsSet()
  36. }
  37. // SetTo sets the boolean with given Boolean.
  38. func (ab *AtomicBool) SetTo(yes bool) {
  39. if yes {
  40. atomic.StoreInt32((*int32)(ab), 1)
  41. } else {
  42. atomic.StoreInt32((*int32)(ab), 0)
  43. }
  44. }
  45. // Toggle inverts the Boolean then returns the value before inverting.
  46. func (ab *AtomicBool) Toggle() bool {
  47. return atomic.AddInt32((*int32)(ab), 1)&1 == 0
  48. }
  49. // SetToIf sets the Boolean to new only if the Boolean matches the old.
  50. // Returns whether the set was done.
  51. func (ab *AtomicBool) SetToIf(old, new bool) (set bool) {
  52. var o, n int32
  53. if old {
  54. o = 1
  55. }
  56. if new {
  57. n = 1
  58. }
  59. return atomic.CompareAndSwapInt32((*int32)(ab), o, n)
  60. }