指尖上的记忆指尖上的记忆
首页
  • 基础
  • Laravel框架
  • Symfony框架
  • 基础
  • Gin框架
  • 基础
  • Spring框架
  • 命令
  • Nginx
  • Ai
  • Deploy
  • Docker
  • K8s
  • Micro
  • RabbitMQ
  • Mysql
  • PostgreSsql
  • Redis
  • MongoDb
  • Html
  • Js
  • 前端
  • 后端
  • Git
  • 知识扫盲
  • Golang
🌟 gitHub
首页
  • 基础
  • Laravel框架
  • Symfony框架
  • 基础
  • Gin框架
  • 基础
  • Spring框架
  • 命令
  • Nginx
  • Ai
  • Deploy
  • Docker
  • K8s
  • Micro
  • RabbitMQ
  • Mysql
  • PostgreSsql
  • Redis
  • MongoDb
  • Html
  • Js
  • 前端
  • 后端
  • Git
  • 知识扫盲
  • Golang
🌟 gitHub

golang的另一种锁竞争解决方案,基于atomic

/**
atomic 原子操作,只针对go中的一些基本数据类型使用:int32、int64、uint32、uint64、uintptr(uintptr 是 Go 内置类型,表示无符号整数,可存储一个完整的地址)
 */
var (
	x int64
	wg sync.WaitGroup
)

func AmAdd() {
	//通过 atomic 原子操作,保证数据操作的原子性,结果一定是500
	atomic.AddInt64(&x, 1)
	//直接x++,非原子操作,数据结果不准确,得到的结果可能是400多
	//x++
	//还可以通过sync.Mutex同步锁实现,加锁性能开销大
	wg.Done()
}

func TestAtomic(t *testing.T)  {
	start := time.Now()
	for i := 0; i < 500; i++ {
		wg.Add(1)
		go AmAdd()  // 原子操作版Add函数,是并发安全的,性能优于加锁版
	}

	end := time.Now()
	wg.Wait()
	fmt.Println(x)
	fmt.Println(end.Sub(start).Seconds())
}




atomic和mutex的区别

1.atomic的包处于sync/atomic,mutex则是sync下的包

2.atomic是对cpu底层进行原子操作,不能通过程序干预。而mutex则是在语言层面的,操作自由度较高。

3.atomic省去了lock和unlock的操作,代码比较简洁

4.atomic因为其在底层就已封装好的特性,所以它在goroutine下的运行表现是连续不间断的;而mutex则在goroutine运行间由于锁的等待或持有等情况,断断续续地执行

5.atomic总体运行较快,但是如果存储数据的非常巨大,它的性能会大打折扣。因为每次更新atomic的数据,都会进行一次数据复制,数据越大效率下降越大