Nevar pievienot vairāk kā 25 tēmas Tēmai ir jāsākas ar burtu vai ciparu, tā var saturēt domu zīmes ('-') un var būt līdz 35 simboliem gara.

88 rindas
2.1 KiB

  1. // Package abool provides atomic Boolean type for cleaner code and
  2. // better performance.
  3. package abool
  4. import (
  5. "encoding/json"
  6. "sync/atomic"
  7. )
  8. // New creates an AtomicBool with default set to false.
  9. func New() *AtomicBool {
  10. return new(AtomicBool)
  11. }
  12. // NewBool creates an AtomicBool with given default value.
  13. func NewBool(ok bool) *AtomicBool {
  14. ab := New()
  15. if ok {
  16. ab.Set()
  17. }
  18. return ab
  19. }
  20. // AtomicBool is an atomic Boolean.
  21. // Its methods are all atomic, thus safe to be called by multiple goroutines simultaneously.
  22. // Note: When embedding into a struct one should always use *AtomicBool to avoid copy.
  23. type AtomicBool int32
  24. // Set sets the Boolean to true.
  25. func (ab *AtomicBool) Set() {
  26. atomic.StoreInt32((*int32)(ab), 1)
  27. }
  28. // UnSet sets the Boolean to false.
  29. func (ab *AtomicBool) UnSet() {
  30. atomic.StoreInt32((*int32)(ab), 0)
  31. }
  32. // IsSet returns whether the Boolean is true.
  33. func (ab *AtomicBool) IsSet() bool {
  34. return atomic.LoadInt32((*int32)(ab)) == 1
  35. }
  36. // IsNotSet returns whether the Boolean is false.
  37. func (ab *AtomicBool) IsNotSet() bool {
  38. return !ab.IsSet()
  39. }
  40. // SetTo sets the boolean with given Boolean.
  41. func (ab *AtomicBool) SetTo(yes bool) {
  42. if yes {
  43. atomic.StoreInt32((*int32)(ab), 1)
  44. } else {
  45. atomic.StoreInt32((*int32)(ab), 0)
  46. }
  47. }
  48. // SetToIf sets the Boolean to new only if the Boolean matches the old.
  49. // Returns whether the set was done.
  50. func (ab *AtomicBool) SetToIf(old, new bool) (set bool) {
  51. var o, n int32
  52. if old {
  53. o = 1
  54. }
  55. if new {
  56. n = 1
  57. }
  58. return atomic.CompareAndSwapInt32((*int32)(ab), o, n)
  59. }
  60. // MarshalJSON behaves the same as if the AtomicBool is a builtin.bool.
  61. // NOTE: There's no lock during the process, usually it shouldn't be called with other methods in parallel.
  62. func (ab *AtomicBool) MarshalJSON() ([]byte, error) {
  63. return json.Marshal(ab.IsSet())
  64. }
  65. // UnmarshalJSON behaves the same as if the AtomicBool is a builtin.bool.
  66. // NOTE: There's no lock during the process, usually it shouldn't be called with other methods in parallel.
  67. func (ab *AtomicBool) UnmarshalJSON(b []byte) error {
  68. var v bool
  69. err := json.Unmarshal(b, &v)
  70. if err == nil {
  71. ab.SetTo(v)
  72. }
  73. return err
  74. }