Go 设计模式

单例模式(Singleton)

  1. package main
  2. import (
  3. "fmt"
  4. "sync"
  5. )
  6. /*
  7. go 单例模式:
  8. 1. 使用 lock,为了并发安全,使用 lock + double check
  9. 2. 使用 sync.Once
  10. 3. 使用 init() The init function is only called once per file in a package, so we can be sure that only a single instance will be created
  11. 参考:
  12. - https://blog.cyeam.com/designpattern/2015/08/12/singleton
  13. - https://golangbyexample.com/all-design-patterns-golang/
  14. - https://medium.com/golang-issue/how-singleton-pattern-works-with-golang-2fdd61cd5a7f
  15. */
  16. var lock = &sync.Mutex{}
  17. type single struct {
  18. }
  19. var singleInstance *single
  20. func getInstance() *single {
  21. if singleInstance == nil { // 防止每次调用 getInstance 都频繁加锁
  22. lock.Lock()
  23. defer lock.Unlock()
  24. // double check. 如果超过一个goroutine进入这里,保证只有一个 goroutine 创建
  25. if singleInstance == nil {
  26. fmt.Println("Creting Single Instance Now")
  27. singleInstance = &single{}
  28. } else {
  29. fmt.Println("Single Instance already created-1")
  30. }
  31. } else {
  32. fmt.Println("Single Instance already created-2")
  33. }
  34. return singleInstance
  35. }
  36. func main() {
  37. for i := 0; i < 100; i++ {
  38. go getInstance()
  39. }
  40. // Scanln is similar to Scan, but stops scanning at a newline and
  41. // after the final item there must be a newline or EOF.
  42. fmt.Scanln()
  43. }
  44. /*
  45. // 使用 once
  46. var once sync.Once
  47. type single struct {
  48. }
  49. var singleInstance *single
  50. func getInstance() *single {
  51. if singleInstance == nil {
  52. once.Do(
  53. func() {
  54. fmt.Println("Creting Single Instance Now")
  55. singleInstance = &single{}
  56. })
  57. } else {
  58. fmt.Println("Single Instance already created-2")
  59. }
  60. return singleInstance
  61. }
  62. */